2013-06-24 1 views
3

Общий вопрос: где хранятся компоненты Java (кнопки, элементы меню и т. Д.), Когда они добавляются к чему-то вроде JFrame, JPanel, JMenu? Когда я просматривал документацию, я увидел, что они хранятся в списке, но я все еще пытаюсь найти конкретную информацию об этой реализации, копаясь в документах Oracle. Может кто-нибудь, кто это понимает, помогает мне понять?Где Java копирует и сохраняет объекты, когда .add'ing их к компоненту Swing?

При перемещении по учебникам Java в Oracle я заметил, что один и тот же идентификатор повторно используется для создания объектов того же типа. Например, это создает две отдельные кнопок:

JPanel buttonPnale = new JPanel("Making some buttons"); 
JButton buttonMaker; 

buttonMaker = new JButton("Left button", blueBurstIcon); 
buttonPanel.add(buttonMaker); 

buttonMaker = new JButton("Right button", orangeBurstIcon); 
buttonPanel.add(buttonMaker); 

Обычно я бы подумал, что мне нужно сделать это:

JButton buttonOne = new JButton("Left button", blueBurstIcon); 
JButton buttonTwo = new JButton("Right button", orangeBurstIcon); 

Созданием отдельного идентификатора, чтобы пойти с каждым отдельным объектом.

Очевидно, объекты в первом фрагменте кода где-то сохраняются, я просто пытаюсь выяснить, где. Должно быть, когда я вызываю .add, что они скопированы - но где они копируются? Если они добавлены в JPanel, они скопированы в структуру данных, содержащую JPanel? Или к структуре данных в части JFrame, к которой добавлена ​​JPanel?

+0

'buttonMaker' - это просто ссылка на' JButton'. Я не уверен, что вы подразумеваете под копией. Внутри 'add()' компоненты сохраняют ссылку, которую они передали. –

+0

Я действительно понимаю, что buttonMaker является идентификатором. Под копией я подразумеваю «установление указателя» - поскольку я предполагаю, что конкретный объект не дублируется, а указатель или ссылка на него бросается в список. Но где этот список? – Azoreo

ответ

3

А JPanel наследует от java.awt.Container, который поддерживает внутренний список клиентских компонентов (ваш JButton з в данном случае). Вы можете найти этот список в исходном коде Container:

/** 
* The components in this container. 
* @see #add 
* @see #getComponents 
*/ 
private java.util.List<Component> component = new java.util.ArrayList<Component>(); 

компоненты добавляют в protected void addImpl(...) метод, который вызывается из метода public Component add(Component comp) в Container.

Так что все это частное. Вы не должны это видеть. ;-)

+0

Спасибо! Это действительно то, что я искал - объяснение того, почему этот материал не появился в Java Docs. Прочитав ответ выше, мне пришло в голову, что это, вероятно, личное/защищенное и не предназначенное для раскрытия. – Azoreo

0

После того, как вы добавили первый buttonMaker, кнопкаMaker ссылается на другой JButton. Первый вызов buttonPanel.add (..) не представляет интереса к тому, для чего была установлена ​​переменная buttonMaker, потому что область действия этой переменной находится только на уровне метода. Эта переменная не существует во второй buttonPanel.add (..) звонок

+0

Я знаю, я спрашивал, где он ссылается, на что я получил ответ (и который делает меня счастливым)! – Azoreo

3

Большинство компонентов Swing содержат список детей. Кадр имеет такой список, и как только вы вызываете add() с кнопкой, кнопка добавляется в указанный список.

Никакой копии не производится. И (неназванная) ссылка в списке, и именованная ссылка buttonMaker указывают на тот же экземпляр в памяти. Некоторые языки называют buttonMaker «псевдоним», чтобы подчеркнуть тот факт, что это не сам объект или экземпляр, а скорее имя для чего-то, что дает вам доступ к экземпляру.

Когда вы назначаете новую ссылку на buttonMaker, это не влияет на кнопки в списке фрейма.

Это также означает, что Java всегда будет видеть кого-то (либо ссылку buttonMaker, либо список), ссылаясь на кнопки, чтобы они не собирались с мусором.

+0

Когда я обсуждал это с моей женой, я понял, что это просто ссылки (прошло некоторое время с тех пор, как я подумал о C.S., что с новым ребенком и всеми). Я предполагаю, что возникла проблема в том, что, просматривая документы Java, ни один «список» не указан в полях - я понял, что каждый элемент данных будет там. Может быть, это личное и не предназначенное для непосредственного доступа? – Azoreo

2

Ну ваш вопрос хороший один .. но да начинающий один ..

В отличие от C, Java не предоставляют вам функции, чтобы пройти через основные блоки памяти, известных как pointers в С. Но да, концепция остается безопасной.

Это связано с тем, что, когда мы говорим о Multi-Threading, тогда такое средство (с использованием указателей в java) позволит столкнуться с памятью. Таким образом, это автоматически обрабатывается JVM. Чтобы сделать Java языком thread-safe.

Кроме того, что вы просите в эквале, это ...

Как создать две кнопки?

Итак, когда вы видите код подробно, он следует за древовидной структурой, то есть JPanel находится на вершине дерева, и вы просто добавляете к нему ребенка. Таким образом, он отслеживает все дочерние узлы. Но если вы просто напишете этот код:

JPanel buttonPnale = new JPanel("Making some buttons"); 
JButton buttonMaker; 

buttonMaker = new JButton("Left button", blueBurstIcon); 
buttonMaker = new JButton("Right button", orangeBurstIcon); 
buttonPanel.add(buttonMaker); 

Затем кнопкаMaker потеряет старую запись кнопки. И добавит вновь созданную кнопку.

Просто помните, то структура дерева, а также указатели (управление памятью) полностью сделано JVM

+0

Правильно, первый объект buttonMaker больше не ссылается и в конечном итоге будет очищен, а второй - фактически добавлен в список. – Azoreo

+0

Посмотрите, что я скажу вам, что это не список. Лучше назовите это деревом ... причина в том, что ... предположим, что у вас есть 1 'JFrame' и есть два' JPanel', и вы добавляете кнопки в свой 'JPanel1' и' JPanel2', поэтому, если бы это был список, тогда структура была бы как JFrame, содержащая один JPanel, который снова содержит JPanel, а затем две кнопки. Но в конечном итоге условие JFrame имеет двух детей (JPanel), и у JPanel есть один дочерний JButton. Так лучше это дерево, а не Лист. –

+0

Да, первый объект - это просто ссылка, и когда объект ссылается на другую кнопку, тогда предыдущее пространство автоматически очищается 'JVM', и вам не нужно беспокоиться об этом явно, как в C. –

0

Использование new вы создаете новые кнопки.

«Должно быть, когда я называю .add, что они скопированы - но где они копируются в случае, если они будут добавлены к JPanel, они копируются в структурой данных JPanel содержит?»

При добавлении этих кнопок в любой JPanel, вы просто поставить ссылку кнопки на внутренней Перечислите JPanel «s (конкретно, вы добавляете ссылку на component списка Container класса, потому что JPanel - подкласс класса Container). Вот source code метода add класса Container.

Снова хочу подчеркнуть, что нет ничего о копировании самого объекта в любом месте при добавлении компонентов в любой контейнер. Его просто добавление ссылок на внутренний список!

+0

I знал, что слово «копия» вернется, чтобы укусить меня! Я понял, что это просто ссылка, меня больше беспокоит, где был проклятый список. Теперь, когда люди показывали мне исходный код, он имеет гораздо больше смысла - спасибо! – Azoreo

+0

Еще вы можете видеть, что я не только предложил вам исходный код, но также упомянул имя списка, которое является «компонентом», которое вы искали! –