Lesson Weekend

Before we move forward, let's discuss one of the most common errors beginning Java students encounter at this point in the course. We'll begin with an experiment. In the REPL, let's compare two strings:

> boolean stringComparison = "hello" == "hello";
boolean stringComparison = true

Here, we create a boolean value called stringComparison and use the == equality operator to see if "hello" is equal to "hello". Predictably, it returns true.

Now, let's do the same comparison, but this time, let's create our strings with constructors. Similar to the constructor we created for our own custom class, Java has built-in constructors for the built-in classes, like String and Integer:

> String firstString = new String("hello");
java.lang.String firstString = "hello"

> String secondString = new String("hello");
java.lang.String secondString = "hello"

> boolean secondStringComparison = firstString == secondString;
boolean secondStringComparison = false

Notice here that despite the two strings both containing the exact same content, "hello", this time the equality operator returns false! Even though it returned true the first time!

== vs equals()

There are actually two primary manners of checking for equality in Java. The == operator, which we've already seen, and the equals() method, which we have not.

==

The == operator evaluates whether two objects or primitives are equal based on the object's location in memory. You know how we can create an object in the REPL, execute a few more lines of code, then refer back to the first object and Java still remembers it?

This is because Java saves variable information in the computer's memory. When we execute the code seen in the example above, two variables named firstString and secondString are both saved into memory.

However, because firstString and secondString are two separate variables (even though they have the similar contents), they are stored in two separate places in the computer's memory. Remember, the == operator evaluates whether things are equal based on the objects' location in memory. So even though both firstString and secondString contain "hello", they're two separate variables, and therefore have two separate places in memory. If we attempt to compare them with ==, it will return false.

The following only returns true because the two strings are never saved into memory. We define them right then and there, in the same statement we compare them:

> boolean stringComparison = "hello" == "hello";
boolean stringComparison = true

equals() method

The equals() method, however, actually compares the values within two strings, not simply the object's location in memory.

Let's perform the exact same comparison we did earlier, using the equals() method instead of ==:

> String firstString = new String("hello");
java.lang.String firstString = "hello"

> String secondString = new String("hello");
java.lang.String secondString = "hello"

> boolean stringComparison = firstString.equals(secondString);
boolean stringComparison = true

And look! It correctly returns true this time around!

Moving forward, always, always, always use equals() to compare Strings. Especially strings that belong to objects. Even though we know == works correctly in limited instances, .equals() will always work.

Overview


  • The == operator evaluates whether two objects or primitives are true based on the object's location in memory.

  • The equals() method, however, actually compares values within strings.

  • This in mind, do not use == to compare strings. If two separate strings are created, even if the strings contain the same exact content they will be saved in two separate places in the computer's memory. == will then return false when comparing them, because it only considers the objects' location in memory.

  • Moving forward, always, always, always use equals() to compare Strings. Especially strings that belong to objects. Even though we know == works correctly in limited instances, .equals() will always work.

Examples


== incorrectly returning false:

> String firstString = new String("hello");
java.lang.String firstString = "hello"

> String secondString = new String("hello");
java.lang.String secondString = "hello"

> boolean secondStringComparison = firstString == secondString;
boolean secondStringComparison = false

equals() correctly returning true:

> String firstString = new String("hello");
java.lang.String firstString = "hello"

> String secondString = new String("hello");
java.lang.String secondString = "hello"

> boolean stringComparison = firstString.equals(secondString);
boolean stringComparison = true