2015-09-25 12 views
2

я задал вопрос по-interview- Сколько объектов создаются на Heap в следующем:Сколько объектов строк создаются на Heap

String s1= "A"; 
String s2= "A"; 
String s3= new String("A"); 

Я ответил 1 - потому, что с новым оператором только , создается строковый объект. Когда компилятор встретит s1, он просто создаст «A» в пуле строковых литералов. И s1 и s2 указывают на один и тот же литерал в литеральном пуле. Но интервьюер смутил меня, сказав, что, где этот пул существует?

Теперь в определенном блог, я прочитал:

«В более ранних версиях Java, я думаю, что до к Java 1.6 Строки буквальный бассейн расположен в PermGen районе кучи, но в Java 1.7 обновляет его перемещаемый к основной области кучи ».

Таким образом, все 3 строковые объекты создаются в куче. Не так ли?

Но s1 и s2 указывают на один и тот же литерал в пуле строковых литералов (s1 == s2 is true), поэтому отдельный объект не должен создаваться, когда встречается s2. Таким образом, необходимо создать только 2 объекта.

Может ли кто-нибудь прояснить как такое количество объектов String на Куча? Я что-то упускаю?

ответ

0

Ответ 1. «А» добавляется в кучу, прежде чем любой из 3-х линий запустить через String Pool, которая существует в куче. Первые две строки ссылаются на существующие значения из пула строк. Третья строка заставляет создать новый объект в куче.

Вот большая рецензия: http://www.journaldev.com/797/what-is-java-string-pool

Примечание: я исправлюсь на комментарий ниже. «A» уже существует в пуле потоков до того, как строка 1 запускается, поэтому в строке ничего не добавляется. Поэтому чистая замена кучи равна 1, как вы сказали в интервью, так как только строка 3 действительно влияет на кучу.

+1

Да - первая строка статьи: «Как следует из названия, String Pool представляет собой пул строк, хранящихся в Java Heap Memory». Изменение в 1.7 для перехода к куче произошло в 2011 году. –

+0

Первая строка ничего не добавляет в пул строк. «A» уже существует, так как класс загружен. Он был первоначально помещен в пул строк файла .class компилятором и объединен с помощью загрузчика классов. – EJP

+0

Спасибо @EJP 5. Обновленный ответ на коррекцию отражения. Должен был спать уже :) –

0

Вы правы. Один объект String создается String s3= new String("A"); и помещается в кучу памяти. Один строковый литерал "A" будет помещен в String pool.

Распределение будет в куче, но оно по-прежнему будет хранить литералы String отдельно и объект, созданный с использованием нового отдельно.

В ранней версии Java, я думаю, что до к Java 1.6 String pool находится в permgen area кучи, но в Java 1.7 обновляет его переехал в основной области кучи. Раньше, так как это было в PermGen space, всегда было опасно создать слишком много объектов String, потому что его очень ограниченное пространство, размер по умолчанию 64 МБ и используемый для хранения метаданных класса, например. .class файлы. Создание слишком большого количества String literals может вызвать java.lang.OutOfMemory: permgen space. Теперь, поскольку String pool перемещен в гораздо больший объем памяти, он намного безопаснее.

enter image description here

Источник: String-literal and String-object

+0

У вас есть какие-либо ссылки, или мы должны просто доверять вам? –

+0

@JonathonReinhart Я обновил свой ответ.Пожалуйста, проверьте – YoungHobbit