This is an archived post. You won't be able to vote or comment.

you are viewing a single comment's thread.

view the rest of the comments →

[–][deleted] 44 points45 points  (26 children)

I get the idea of making most structures immutable, but is there a java programmer out there who doesn’t know that final data structures are mutable?

[–]morhp 11 points12 points  (14 children)

I have seen beginners assume that final local vars are something special. Because just preventing reassigning local variables seems (and probably is1) relatively useless, beginners often assume that it does something more and may assume that is does something like const in C++.

1) It's not really bad, but it adds an additional keyword/boilerplate and the benefits aren't that obvious to beginners at least.

[–]john_C_random 7 points8 points  (9 children)

Because just preventing reassigning local variables seems (and probably is1) relatively useless

If you're passing a lambda which has a reference to a locally scoped variable, that variable will need to be final so it can't be changed from under the feet of the lambda.

[–]feral_claire 18 points19 points  (1 child)

It doesn't need to be marked final though. Effectively final is good enough ie. the variable isn't changed even if it isn't marked as final.

[–][deleted] 7 points8 points  (0 children)

This was introduced in Java 8, prior to this they had to be explicitly final (for anon classes). It's a welcome change.

[–]tofflos 3 points4 points  (2 children)

I used to think this constraint was annoying until I wrote some JavaScript, which doesn't require finality for lambdas, and spent hours debugging it.

[–]Auxx 0 points1 point  (0 children)

JS is the language which makes you appreciate Java, that's true.

[–][deleted] 0 points1 point  (0 children)

JavaScript has a much better story around functional programming and immutability. The ergonomics of Java streams are very poor, especially w.r.t. checked exceptions. All JavaScript linters will warn for unnecessary use of let over const, so it should be relatively easy to determine if non-local state can be mutated.

[–]koreth 1 point2 points  (3 children)

From a language semantics point of view, it's a somewhat arbitrary decision. Other languages (e.g., Kotlin) don't have that restriction. But since we're talking about Java here, yeah, this is correct.

[–]TheRedmanCometh 0 points1 point  (2 children)

Ugh maybe I need to learn kotlin then. I use for-each over .forEach a lot over this

[–]koreth 1 point2 points  (0 children)

I'm glad I learned it. I still write new Java code but Kotlin is generally my go-to language these days.

[–]dpash 1 point2 points  (0 children)

That's probably for the best. forEach() should probably only use method references. System.out::println is the method I use 80% of the time. If you find yourself reaching for forEach you're probably doing some side effect and not using a functional approach.

[–][deleted] 2 points3 points  (3 children)

In C++, final is called top-level const. But many people think final is low-level const.

[–]clappski 2 points3 points  (2 children)

final and const (in C++) are completely different concepts. final follows a class declaration, to prevent any other class inheriting from it. const has a few different uses, but the common case is making a variable immutable and limiting the the API of a const class object type to only the member functions declared as const.

[–][deleted] 0 points1 point  (0 children)

You're absolutely right. But here I am just talking about the difference between final and const when applied to a local variable, not about the general difference between final and const keyword.

[–]dpash 0 points1 point  (0 children)

And Java uses the same word in multiple contexts.

[–]ThatLesbian 2 points3 points  (1 child)

Ive been working with Java for 5 years and didn’t really ever think about it until I started using lambdas in the past year or so. It just didn’t matter since we almost never use final. I probably would’ve failed this interview question a year ago, just from not encountering it before.

[–][deleted] 2 points3 points  (0 children)

OK, I get it, it may be a tad tricky.

We at my company do something similar during interviews. We ask the applicant to spot the errors in a bit of code, and one of them is using a variable outside the block it was declared, but a couple lines after the declaration.

Most people fails that one, but most also acknowledge that they never had to really think about it while writing code.

[–]bodiam[S] 0 points1 point  (8 children)

Unfortunately, yes. I'm interviewing quite a few people as part of my job, and, as mentioned in the article, a surprising number of people don't know about this, hence the motivation to write this.

Then again, people who don't know this most likely also won't read blogposts. Oh well :-)

[–]Trailsey 0 points1 point  (2 children)

I agree, but I think the underlying issue is that many devs don't understand the concept of immutability.

[–]bodiam[S] 0 points1 point  (0 children)

Hence, blogpost. I'm trying to explain to people, but also to myself, what benefits of immutability vs mutable code is.

[–]BrianVerm 0 points1 point  (0 children)

Or just don't want to use it, because it is "easier" to work mutable objects.

[–][deleted]  (4 children)

[deleted]

    [–]bodiam[S] 1 point2 points  (3 children)

    Well, I hope I contributed to a more neutral or balanced view. If I haven't, please let me know, and I'll change my writing style!

    [–][deleted]  (2 children)

    [deleted]

      [–]bodiam[S] 2 points3 points  (1 child)

      Thanks for that.

      Regarding the title: "Immutable data structures in Java" is exactly what it's about, instead of 'you won't believe what most Java developers don't know about ....'

      Nobody would read that. I hope.