Java Java Data Structures Efficiency! Implement Chooser UI

Pavle Delic
Pavle Delic
8,088 Points

byArtist method question

I am confused about position of the line: "byArtist.put(song.getArtist(), artistSong)"; Why is it inside if statement? Isn't that mean that we will add a key with the null value, if the key is missing? At the end of video, it was demonstrated that it works, he added two M. Jackson's songs, but I need an explanation, how it works.

My understanding is that last line "artistSongs.add(Sond)" is doing nothing, without "byArtist.put(song.getArtist(), artistSong)" after it.

Please help me understand it.

1 Answer

andren
andren
28,383 Points

Lists in Java are a bit special, they act like reference-type objects, which basically means that when you store a list in a variable you don't get a copy of the list, you get a value that points to a location in memory where the list is actually stored.

To illustrate the difference this makes compared to a more traditional object like a String or int let's look at a code example:

List<String> example1 = new ArrayList<>();
example1.add("a");

List<String> example2 = example1;
example2.add("b");

for (String string : example1) {
    System.out.print(string);
}

What would you expect the above code to print out, "a" or "ab"? The answer is actually "ab" even though you would likely expect the answer to be "a".

The reason is that when you define example2 as being equal to the example1 List the two variables now point to the same List in memory, they don't store independent copies of the list. They point to the exact same list. So adding a value to example2 will also add it to example1.

So with that knowledge let's take another look at the code from this video:

List<Song> artistsSongs =  byArtist.get(song.getArtist());

That line will get a reference to the Song list stored in the byArtist map, if that line returns null which it will do if no key with the artist name exists then the code within the if statement will run:

aristSongs = new ArrayList<>();

That line creates a new ArrayList instance and stores it in the aristSongs variable.

byArtists.put(song.getArtist(), aristSongs);

That line creates an entry in the byArtists map with a key of the artists name and a value that stores the instance of the list we created in the above line.

Then this line runs:

artistSongs.add(song);

That line adds the song to that list we created. Since the list stored in artistSongs is not independent of the list stored in the map adding a song to it will also add a song to the list stored in the map. Therefore you don't need to insert the list into the map again.

If this method runs and does not return null:

List<Song> artistsSongs =  byArtist.get(song.getArtist());

Then the if statement is skipped and you simply get a reference to the list and add the song to it:

List<Song> artistsSongs =  byArtist.get(song.getArtist());

Which works exactly the same as in the previous example. The list in the map has the song added to it since it points to the same list as the artistsSongs variable points to.

Pavle Delic
Pavle Delic
8,088 Points

Thank You for a very comprehensive and helpful answer. I suspected on something like that, but the first line of for loop was giving me trouble, but now I think I understand it. I was thinking about that references between lists, but on next iteration, list with the same name is getting a new value. Now I realize that is actually breaking the connection with the list from previous iteration, and creating new one, changing it's reference. So the list from previous iteration is stays unchanged.

Andre Kucharzyk
Andre Kucharzyk
4,479 Points
"artistSongs.add(song);

"That line adds the song to that list we created. Since the list stored in artistSongs is not independent of the list stored in the map adding a song to it will also add a song to the list stored in the map. Therefore you don't need to insert the list into the map again."

@andren Could you elaborate on that, please? What do you mean by saying "the list stored in artistSongs is not independent of the list stored in the map "? You mean because of this line of code is independent?: List<Song> artistSongs = byArtist.get(song.getArtist());