Using isFancy
for a setter is certainly not a standard convention and may therefore confuse the code's readers. However, the idea of using a fluent interface is a good one. If I had to choose a name for use in your second example, I would simply use fancy()
. This is a name which you can use for both the setter and getter without confusing anyone, and it is shorter than the names with set/get prefixes. Note, however, that some IDEs and other tools may not work as well if your getter/setter do not have the prefixes in their names.
Yet another thing which I like to do is making my data objects immutable. Some languages (e.g. Kotlin and Scala) make using immutable data classes even easier, but this style of programming works with Java as well. It makes functional programming easier and allows you to avoid some kinds of errors, especially in parallel code. You can combine immutability with your second approach by using a separate builder class. This adds some lines of code, but (assuming there is more than just one field), the overhead is not that bad and later the resulting object is quite pleasant to use:
public final class MyClass {
private final boolean fancy;
private MyClass(boolean fancy) {
this.fancy = fancy;
}
public static Builder builder() {
return new Builder();
}
public boolean fancy() { return fancy; }
public static class Builder {
private boolean fancy = false;
public fancy(boolean fancy) { this.fancy = fancy; }
public MyClass build() { return new MyClass(fancy); }
}
}
An added advantage is that you can set reasonable defaults in your builder. You can also pass the builder around between methods as long as the object is being constructed, so for example fancy value can be set in several different places if that's needed, but once you create the final object via build()
, it is immutable and thus threadsafe (and you know that at this point it can't be modified in any unintended way).
So the short way of building your object is:
builder().fancy(true).build();
but you can also split it into multiple calls:
Builder builder = builder();
builder.fancy(result_of_some_calculation)
// do other stuff
if (something) {
builder.fancy(result_of_another_calculation)
}
callSomeMethod(builder.build())
Of course, the more fields you have, the more use you will gain from using the builder pattern with immutable data class.
setFancy
vsisFancy
does not stop you from returningthis
and then doingMyClass myClass = new MyClass().setFancy(true);
in a fluent way. Sure the naming would feel a bit odd, so if you are going Fluent then maybeisFancy
is better. But if going Fluent then I would rather have a fluent Builder with an immutable object.set<prop>
for aboolean
feels a bit odd. I also considered using the builder approach but when the class is relatively small, having a builder seems a bit too much. Great suggestion though thanks!isFancy()
andisNotFancy()
to set or clear the fancy flag that would also work.