2

I was reading about String in java and was trying to understand it.

At first, it was easy how String s1="11" and String s2=new String ("11") works(created) and I understood intern method also.
But I came across this example (Given by a friend) and made me confused about everything.

I need help to understand this.

String s1 = new String(new String("2")+new String("2"));
s1.intern();
String s2="22";
System.out.print(s1==s2);  //=>true as output.
String s3 =new String (new String("2")+new String("2"));
s3.intern();
String s4="22";
System.out.print(s3==s4);  //=>false as output.

Answer of this code is true and false.

Part for S1 and s2 was good and was true according to my understanding but the second part I didn't understand.

Hope someone can break the code line by line and help me understand.

8
  • String references are immutable. s3 = s3.intern(); And you'll get true. As for the first example, look at the order of execution - put String s2 = "22"; before String s1 = //... for false. Commented Mar 19, 2017 at 6:28
  • @ElliottFrisch could you elaborate more on the first case. I find both the cases same, except we have different variables. How come on the first case we get true, while the second one gives false, even though the order of execution is same for both the cases Commented Mar 19, 2017 at 6:33
  • Move the declaration of s2 to before s1 for a surprise. And then move it to before the s1.intern(); for the same surprise. Finally, s2 is the same reference as s4 (s2 == s4 is true). Commented Mar 19, 2017 at 6:36
  • Thanks @EJP for edit Commented Mar 19, 2017 at 7:05
  • @ElliottFrisch LOL i am all suprised and shocked But there must be answer for this . Both situation are same declaration and assignment on both cases are exact replica. But the question remains why true for one and false for other Commented Mar 19, 2017 at 7:08

5 Answers 5

2

s1.intern(); adds s1 to the pool of strings, therefore the string "22" is now in the pool of strings. Therefore when you write s2 = "22" that's the same "22" as s1 and thus s1 == s2.

s3.intern() does NOT add s3 to the pool of strings because the string "22" is already there.

s3.intern() does return that same "22" which is s1 BUT IT IS NOT USED. Therefore s3 is not equal s4.

Sign up to request clarification or add additional context in comments.

Comments

0

In java exist the heap and the stack, Heap is where all Objects are saved stack is where vars are saved Now also exist another kind of list for Strings and Integers (numbers)

As you know a String can be created in some ways like

like new String("word") or just = "word" when you use the first way you create a new object (heap) when you use the other you save the word in a stack of words (Java engenniers thought it would be good if you don't create manny objects or words are repeated so they created an special stack for words, same for Integers from 0 to 127) So as I said You have to know that there is an stack and a Heap look at this example

String wordOne ="hola";
        String wordTwo = "hola";
        String wordTres = "hola";
        System.out.println(wordOne == wordTwo);
        System.out.println(wordTres == wordTwo);
        System.out.println(wordOne == wordTres);

        String wordFour = new String("hola");
        System.out.println(wordOne == wordFour);

        Integer uno = 127;
        Integer dos = 127;
        System.out.println(uno == uno);
        Integer tres = 128;
        Integer cuatro = 128;
        System.out.println(tres == cuatro);

String x = "word"; is saved in an special Stack String y = new String("it is not");

But tbh I don't remeber so well the rules for tha stack, but in any case i recomend you to compare all words using wordX.equals(wordY)

An also numbers in objects could be compared using == from 0 to 127 but the same if you use objects use equals, although using numbers there is a better do to do it in spite of use equals, convert one number to a primitive value (the memory will be better)

enter image description here

Comments

0

When you are making string with new keyword,JVM will create a new string object in normal(non pool) heap memory and the literal will be placed in the string constant pool. In your case, The variable s1 will refer to the object in heap(non pool).

String s1 = new String(new String("2")+new String("2"));

But in the next line your are calling intern() method.

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.

Check Javadocs. As "22" is not in string pool, a new string literal "22" will be created and a reference of it will be returned. When you are writing:

String s2="22";

it simply refers "22" in string pool. But calling s3.intern() will not create a new string literal as "22" exists in the pool. Check the Javadocs for intern() again. It says if exists in pool, then string from the pool is returned not reference. So, this time s3 references to a different object. But s4 is referred to same object as s1,s2. You can print the objects hashcode for checking if the are same or not. Like:

System.out.println(System.identityHashCode(s1));

Comments

0

Notice that the type String is capitalized and is not one of Java's 8 primitive types (int, boolean, double, char, etc.). This indicates that any instance of a String is an object that was built using the 'blueprint' of the class String. Because variables in Java that refer to objects only store the memory address where the actual object is stored, when you compare Strings with == it compares memory location.

String str1 = new String("hello");
String str2 = str1; //sets str1 and str2 pointing to same memory loc
if (str1 == str2){
    //do stuff; the code will enter this if-statement in this case
}

The way to compare the values within objects in Java is with equals(), such as:

String str1 = new String("hello");
String str2 = new String("hello"); //str2 not same memory loc as str1
if (str1.equals(str2)){
    //do stuff; the code will enter this if-statement in this case
}

This is a common error for beginners, since the primitive types are not objects and you CAN compare two ints for equality like:

int one = 1; //primitive types are NOT objects
int two = 2; //notice when I make an int, I don't have to say "new"
             //which means a new **object**
if (int1 == int2) {
    //do stuff; in this case the program will not enter this if-statement
}

It seems that you understand everything but the meaning of the very last line. See my comment on the last line.

String s1 = new String(new String("2")+new String("2")); //declare AND initialize s1 as a new String object
s1.intern();
String s2="22"; //declare a new variable s2 and point it to the same object that s1 is pointing to
System.out.print(s1==s2);
String s3 =new String (new String("2")+new String("2"));
s3.intern();
String s4="22";
System.out.print(s3==s4); //check if s3 and s4 are stored in the same memory location = FALSE

5 Comments

this answer no where related to the question. The question isn't about the difference between == and equals, if it was it would have been marked as a duplicate.
You're right. I was just trying to supplement the other answer. But I edited my answer to fit the question better.
@ashtree But what about s1==s2 ? Why it returns true. Both scenario are exact same .
Look at the statement when String s2 is declared but, importantly, NOT initialized with new and an object. You're NOT saying something like String s2 = new String("hello"); ... you're saying, I declare String s2, and it is a variable that is now set to an already existing object s1 ( once again, because we're not creating a new one with the new keyword). The variable s1 is a reference to a location in memory because it is associated with an object. s1 was created with new and String("dog"); but s2 was NOT.
@aatif I added a couple more comments in my answer describing your code line by line. Let me know if there are any more lines that need clarifying.
-2

In java object1 == object2 means

that do object1 and object2 have the same address in memory?

object1.equals(object2)

means are they equal, for example do they have the same values of all fields?

So, For two Strings S1 and S2, string1.equals(S2) means, do they have the same characters in the same sequence?
S1 == S1 means are string1 and string2 stored at the same address in memory?

3 Comments

This completely fails to address any aspect of the OP's question.
@Hamza Sorry bro but it is not about equals and ==. Please read and look at the question again.
I was clearing the fact about the memory references and values. I know it is not about equals but in detail, it is about referencing.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.