• Post Reply Bookmark Topic Watch Topic
  • New Topic
programming forums Java Mobile Certification Databases Caching Books Engineering Micro Controllers OS Languages Paradigms IDEs Build Tools Frameworks Application Servers Open Source This Site Careers Other Pie Elite all forums
this forum made possible by our volunteer staff, including ...
Marshals:
  • Campbell Ritchie
  • Tim Cooke
  • paul wheaton
  • Liutauras Vilda
  • Ron McLeod
Sheriffs:
  • Jeanne Boyarsky
  • Devaka Cooray
  • Paul Clapham
Saloon Keepers:
  • Scott Selikoff
  • Tim Holloway
  • Piet Souris
  • Mikalai Zaikin
  • Frits Walraven
Bartenders:
  • Stephan van Hulst
  • Carey Brown

String Pool Redux

 
Bartender
Posts: 2205
  • Likes 1
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Ok, this issue of string pool allocation objects has been wearing on me so I decided to write a little test program to see if these objects are in fact ever garbage collected. Guess what? They are!

This program runs in an endless loop continuously creating a unique string, then adding that string to the string pool. Every 10,000 new strings, it prints out a diagnostic message showing the total memory for the VM and the free memory available. You'll notice if you run this that the free memory fluctuates,but never gets below around 25 %. Garbage collection is clearing these string pool objects!!
To verify that objects are really being created you can uncomment line 1. This adds the string to an ArrayList, thus keeping a strong reference to the object, preventing it from being garbage collected. If you do this, you will run out of memory.
This test application shows that java does in fact clear out the string pool during garbage collection; as long as no objects are referencing an object in the string pool, they get treated like any other object that is not referenced-they become eligible for garbage collection.

Rob "string literal mystery solver"
 
Ranch Hand
Posts: 732
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
amazing Rob!
well done.
thanks for solving this mystery
 
Ranch Hand
Posts: 5399
1
Spring Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi Rob
Thanks a lot.
I think question was from the Exam view of point and for normal small peiece of code like this
1. public void process(int count) {
2. for ( int i = 1; i < count; i++ ) {
3. Object temp = " Hello "+i; }
4. }
do we have to consider the GC of string litral as you can see by running your program that after capaturing(creating objects) lot of memory it is freeing String litrals.
and if we are going to consider GC of litrals then what abt StringBuffer which are being created internally .
So I think from the Exam point of view answer should be 4.
CMIW
 
Ranch Hand
Posts: 2120
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
newString.intern() is not a string literal.
The program shows that string objects that are interned are g.c.ed
The code that shows how string literals are not g.c.ed is here:
www.javaranch.com/ubb/Forum24/HTML/012708.html
Your program is interesting because shows that a programmer can not run out the heap by interning many string objects.
Later I will post a program to see how "Hello".intern() behaves
 
Ranch Hand
Posts: 203
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator


Rob "string literal mystery solver"


Very TRUE. Great program Rob. Now we can lay this topic to rest!
 
R K Singh
Ranch Hand
Posts: 5399
1
Spring Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Originally posted by Jose Botella:

newString.intern() is not a string literal.


but I think it put your this stirng in litral pool if not available.
CMIW
 
Jose Botella
Ranch Hand
Posts: 2120
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
First of all, I think we are splitting hairs.

Second I don't expect questions regarding the reachability of string literals in the exam.
Third. String literals are not g.c.ed
Fourth. newString.intern() is not a string literal. It places a string object in the string pool.
Rob's program shows that these object though in the string pool are g.ced
Thanks Rob, I din't know that
This program shows that String literals that are computed at compile time (JLS 15.28) are not g.ced

The string literal is always reachable, though you can see sucessives g.c.tions if you run like "java -verbose:gc Test" When the strinCount reaches 200000 I expect the first string object is already g.c.ed It is, because it prints null. My intention was to demonstrate how the weak reference doesn't prevent an object of being g.c.ed
My conclusion is that string literals are not g.c.ed but others string objects, even in the pool, are.
Also be careful with this:

Is there anyone still confused , just remember the first two points of this post
[ January 21, 2002: Message edited by: Jose Botella ]
 
Rob Ross
Bartender
Posts: 2205
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Jose,
I was just about to respond when I saw you have posted a long test program, so I haven't looked at it yet, but I will.
The main confusion I am having about the "string pool" is that there seems to be two of them, one for interned strings, and one for string literals, even though I can't find *any* literature that explains the difference. Even the javadocs for the String.intern() method suggest there is only one pool...


intern
public String intern()
Returns a canonical representation for the string object.
A pool of strings, initially empty, is maintained privately by the class String.
When the intern method is invoked, if the pool already contains a string equal to this String object as determined by the equals(Object) method, then the string from the pool is returned. Otherwise, this String object is added to the pool and a reference to this String object is returned.
It follows that for any two strings s and t, s.intern() == t.intern() is true if and only if s.equals(t) is true.
All literal strings and string-valued constant expressions are interned. String literals are defined in �3.10.5 of the Java Language Specification
Returns:
a string that has the same contents as this string, but is guaranteed to be from a pool of unique strings.


If what you are saying is true, it seems the javadoc for String.intern() is incorrect?
I'll look at your new program later today and comment later

Rob
 
R K Singh
Ranch Hand
Posts: 5399
1
Spring Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi Jose
as u say .. no more splitting hairs
so answer is 4 ahahaha

I don't expect questions regarding the reachability of string literals in the exam


agreed



FOR a time being .... if possible then anyone
what is going on here

what is the difference betn LINE 01 and LINE 02.
would luv to hear from jose.
(Yes it can be put in to Adv Java, but then you should provide some mechanism to get informed to other threads also if some reply comes.)
TIA

 
R K Singh
Ranch Hand
Posts: 5399
1
Spring Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Originally posted by Rob Ross:
Jose,
The main confusion I am having about the "string pool" is that there seems to be two of them, one for interned strings, and one for string literals, even though I can't find *any* literature that explains the difference.
Even the javadocs for the String.intern() method suggest there is only one pool...


No.. doc just says they are interned
I think they two places for String pooling.. one for String litral and one String constants(generally which appear betn S.o.p)
CMIW



If what you are saying is true, it seems the javadoc for String.intern() is incorrect?


this might be the case plz see
I checked source .... intern is native method!!!
but still I think ans is 4
[ January 22, 2002: Message edited by: ravish kumar ]
 
Jose Botella
Ranch Hand
Posts: 2120
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
to Rob
I don't mean API for intern is wrong.
I don't really know if there are two string pools.
I only state that string literals and String expressions computed at compile time (JLS 15.28) are not g.c.ed

to Ravish
I don't mind splitting hairs with any well-mannered Rancher in pursuit of Java knowledge.

Hey, you forgot making str01 null
For completness I am posting this code

According to JLS 15.28 "Hello " + j is a constant expression computed at compile time. They are not g.c.ed
 
Rob Ross
Bartender
Posts: 2205
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
All literal strings and string-valued constant expressions are interned
That's from the JavaDoc for String.intern();
It states right there that literal strings are interned!
So if you are correct Jose, it means that there is one of three explanations:
1. a special literal intern pool exists seperate from the "regular" intern pool, that I can't find any documentation for
2. this java doc is wrong and literals are not interned; something else happens to them
3. string literals in the intern pool have some special, "magical" state that prevents them from being gc while other strings in the intern pool created with String.intern() can be gc.
I don't like any of these alternatives only because I can't conclusively prove which one is actually the case.
But your code example supports your statement that string literals aren't gc. Of course, being the scientist, I can't say it *proves* your point, only that it supports it. However, I am now leaning towards the side of thinking that string literals exist for the life of the program. But this still leaves me with the above unanswered questions.
I need to *know* this, not just take it on faith!
Thanks for your input so far!
Rob
 
R K Singh
Ranch Hand
Posts: 5399
1
Spring Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I got it ..........
I am assh@#$...
but Jose you too....


I only state that string literals and String expressions computed at compile time (JLS 15.28) are not g.c.ed


and what so ever is being GCed are interned at runtime as stringCount or what so evar variable we are concating .... so interned at RUNTIME could be GCed.
Now I am 100% sure that COMPILE time string litrals are not GCed BUT RUNTIME string litrals are GCed
as you said Jose it is there in (JLS 15.28) (I have not checked)...
CMIW
 
Jose Botella
Ranch Hand
Posts: 2120
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hello everybody
I have the answer at last.
String literals and String objects computed from constant expressions (JLS 15.28) are not g.c.ed becuase a reference is hold to them in the constant pool of the class that declares them. Thus even seeting all the programmers reference to null they will keep on being pointed to by the constant pool as long as the class data is loaded.
To check this I have written a class that creates several of these objects:

At lines 10, 16, 0 and 3 you can see ldc# 3, 5, 7 and 8 bytecodes. They load the reference to a string object from the constant pool to the operand stack. Thus entries 3, 5, 7 and 8 in the constant pool are to blame for the almost permanet reachability of these kinds of objects. Well, permanet? not really. We can download the class Test2, and doing so its constant pool disappears. Now these objects are g.c.ed
This progrma shows it:

I have not more time now. I am going to my dancing classes
 
Jose Botella
Ranch Hand
Posts: 2120
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I forgot to mention that Test2.class is in "other" directory, under the current one where Test.class is executed.
 
Rob Ross
Bartender
Posts: 2205
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hey good work Jose.
I had just read up on how to unload a class by using a custom class loader!
But you are right...every .class file has a private constant table, and for string constants, they are references to a String object in the string pool. So you are correct, as long a class is loaded, all string literals used by that class create a strong reference to a String object in the pool and thus never are eligible for gc.
I finally feel I have a good understanding of how this works.
The important issue is that in code, a string literal is just the constant string expressions that can be computed at compile time.
String myString = "I am a string"+" composed of two segments, but I am one string literal";
int i = 5;
String aString = "This is a string literal "+i;
aString above, is NOT a string literal because its value must be computed at runtime. There is only one string literal above, and that is the text between the quotes.
Anyway, thanks for shedding light on this matter once and for all Jose!
Rob
 
R K Singh
Ranch Hand
Posts: 5399
1
Spring Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Originally posted by Rob Ross:

String myString = "I am a string"+" composed of two segments, but I am one string literal";
int i = 5;
String aString = "This is a string literal "+i;
aString above, is NOT a string literal because its value must be computed at runtime. There is only one string literal above, and that is the text between the quotes.
Anyway, thanks for shedding light on this matter once and for all Jose!
Rob


that's what I said ....
I like this thread ...Jose I will check your prog soem other day...
till then
 
Can you shoot lasers out of your eyes? Don't look at this tiny ad:
Smokeless wood heat with a rocket mass heater
https://woodheat.net
reply
    Bookmark Topic Watch Topic
  • New Topic