Live data from Hacker News

Never Use toString() for Behaviour

java.christmas

21–30 of 51 posts

Re: Never Use toString() for Behaviour

#21
post #3

That was a complete waste of time. To sum it up: don't rely on the format of a generic toString() method. Prefer country.getName() over country.toString(), even if toString() returns getName().

A complete waste of time for some, and very useful for others. I don't believe comments like this is constructive for anyone.

Yeah, I was a bit harsh. But they already posted an announcement post about their Christmas calendar: https://news.ycombinator.com/item?id=21700759 I don't see the need to go into individual posts on top of it.

In the end, I just think there are better channels for getting started with programming in a particular language then this site.

Re: Never Use toString() for Behaviour

#22
post #14
post #13

Never use a language that puts a toString() implementation on every object regardless of whether or not that object implements toString()

The ability to convert any object to a string is very useful for debugging and most languages support this. Even in C it's frequently useful to print %p to identify objects. Serialization should require involve separate APIs.

That %p approach sounds perfect.

If they wanted to make it worse, they could make it so you could call %s on any object, and if it wasn't defined, it would "conveniently" fall back to %p instead.

Then someone could could write an article called "Never Use %s for Behaviour"

Re: Never Use toString() for Behaviour

#23

> If you used the returned Country to construct an API request including the name of the country, this will now produce strange countries named as “Optional[“Norway”]” I am not too familiar with java, but should’t you call get() from optional to get Country from Optional and toString of Country will behave as expected.

As the sibling comment says, the post's advice is really about making your code refactoring-friendly with regard to type checking.

You generally would not want to call '.get()' without an 'isPresent()' check because it will throw a NoSuchElementException if the Optional is empty. This is a foreseeable case, so most would like to handle it somewhat explicitly.

Today, it is idiomatic to use '.map' to transform it:

    Optional foo = optionalCountry.map(Country::getName);
You can also throw a domain-specific exception from that point:

    Optional foo = optionalCountry
        .map(Country::getName)
        .orElseThrow(...);

Re: Never Use toString() for Behaviour

#26
post #2

Agree in general, but note that Java itself does not follow this rule: StringBuilder's and StringWriter's toString methods use toString for behavior — creating a string from accumulated chars, and I'm fine with that.

The typical usage for StringBuilder tends to make it pretty obvious you're using a StringBuilder and everybody expects you will convert to a string at the end. Usually StringBuilders are short lived and all the calls and the declaration are close to each other.

Re: Never Use toString() for Behaviour

#27
Java's eccentric uncle Objective-C called this method "description" instead of "toString". That was a better name IMO because it avoids the suggestion that it's some kind of canonical string representation.

Re: Never Use toString() for Behaviour

#28
post #5

>If left unoverridden, it only yields a description of it’s class and location in memory It contains the hashCode(), not the memory location. The default implementation of hashCode could use a memory location to generate the hash, however that isn't the case in all implementations. OpenJDK seems to have used an RNG by default in the past and currently derives a value from the thread state[1] [1] https://srvaroa.githu…

for most implementations it would not be possible to use the location in memory because most java garbage collectors will move stuff around in memory. they could use the location initially and cache it afterwards but this would seem tricky to do without breaking the hash code contract.

Re: Never Use toString() for Behaviour

#30
post #2

Agree in general, but note that Java itself does not follow this rule: StringBuilder's and StringWriter's toString methods use toString for behavior — creating a string from accumulated chars, and I'm fine with that.

The typical usage for StringBuilder tends to make it pretty obvious you're using a StringBuilder and everybody expects you will convert to a string at the end. Usually StringBuilders are short lived and all the calls and the declaration are close to each other.

Ok, but then the rule is not to use toString() for behavior unless it "makes sense" to do so, which is not a rule at all.
Post reply on HN