On the other hand, value semantics are just plain easier to reason about.
My 2 is your 2. We don't have different 2s because it makes no sense.
But sometimes you don't just want a 2, you want a pair (2,3). All of a sudden, my (2,3) isn't your (2,3), unless you call equals instead of ==, and remember to implement equals() (and that demands implementing .hashcode() too, and probably a toString() while you're at it). While it's easy to forget about if you've been using Java for a while, 2 gets passed by value, but your pair gets passed by pointer-value.
So I'd come at it from the other side. Pick a value representation of (2,3), reap the simplicity, and hope the sufficiently smart compiler is smart enough to do good things with it.
Comments
On the other hand, value semantics are just plain easier to reason about.
My 2 is your 2. We don't have different 2s because it makes no sense.
But sometimes you don't just want a 2, you want a pair (2,3). All of a sudden, my (2,3) isn't your (2,3), unless you call equals instead of ==, and remember to implement equals() (and that demands implementing .hashcode() too, and probably a toString() while you're at it). While it's easy to forget about if you've been using Java for a while, 2 gets passed by value, but your pair gets passed by pointer-value.
So I'd come at it from the other side. Pick a value representation of (2,3), reap the simplicity, and hope the sufficiently smart compiler is smart enough to do good things with it.