Showing posts with label Setter. Show all posts
Showing posts with label Setter. Show all posts

Sunday, June 12, 2011

Builder style setters or Chained invocation in Java

Setters idiom in Java is an evil and I hate it. And I don't hate it because you have to invoke setXXX methods multiple times when you have to set many fields. The most annoying thing for me is that you can only set one field in a line. This is because setter method return this stupid void. Here is the example:

public class Car {  
private int maxSpeed;
// remainder omitted

public void setMaxSpeed(int maxSpeed) {
this.maxSpeed = maxSpeed;
}
// remainder omitted
}

So my code using the Car class will look like this:

Car car = new Car();  
car.setMaxSpeed(210);
car.setSpeedUnit("km/h");
car.setLength(5);
// remainder omitted


I have an idea how the life of the developers can be made easier using builder-style setters "pattern". Here is the new BETTER Car class:


public class Car {  
private int maxSpeed;
private String speedUnit;
// remainder omitted

public Car setMaxSpeed(int maxSpeed) {
this.maxSpeed = maxSpeed;
return this;
}

public Car setSpeedUnit(String speedUnit) {
this.speedUnit = speedUnit;
return this;
}
// remainder omitted
}


I can now instantiate and initialize my Car object in one line (maybe wrapped but still one line of code):

Car car = new Car()  
.setMaxSpeed(210)
.setSpeedUnit("km/h")
.setLength(5)
...


What do you think? Isn't it much easier now? Of course if you extend Car class it becomes more tricky as you have to repeat all the setter methods like this:

public class Truck extends Car {  
private int capacity;
private String capacityUnit;
// remainder omitted

@Override
public Truck setMaxSpeed(int maxSpeed) {
super.setMaxSpeed(maxSpeed);
return this;
}

@Override
public Truck setSpeedUnit(String speedUnit) {
super.setSpeedUnit(speedUnit);
return this;
}
// remainder omitted
}


Looking at the better use case


The example is not very good above, so please bear with this. Actually when there is class hierarchy having full inheritance among them, example – There is a class called Person as the Base class. Now suppose GrandParent extends Person, Parent extends GrandParent, Child extends Parent. Now the common properties of these can be set by some interface say ISetter (stupid name, please ignore).


Now all the common settings can be set by implementing ISetter interface and that will be kind of one-liner, increasing the code readability.

Saturday, March 12, 2011

Java beans

A Java bean is just an object that has certain characteristics. The class that defines a Java bean must be a public class. It must have a constructor that takes no parameters. It should have a "get" method and a "set" method for each of its important instance variables. The last rule is a little vague. The idea is that is should be possible to inspect all aspects of the object's state by calling "get" methods, and it should be possible to set all aspects of the state by calling "set" methods. A bean is not required to implement any particular interface; it is recognized as a bean just by having the right characteristics. Usually, Java beans are passive data structures that are acted upon by other objects but don't do much themselves.

Getters and Setters OR Accessors and Mutators

When writing new classes, it's a good idea to pay attention to the issue of access control. Recall that making a member of a class public makes it accessible from anywhere, including from other classes. On the other hand, a private member can only be used in the class where it is defined.
In the opinion of many programmers, almost all member variables should be declared private. This gives you complete control over what can be done with the variable. Even if the variable itself is private, you can allow other classes to find out what its value is by providing a public accessor method that returns the value of the variable. For example, if your class contains a private member variable, title, of type String, you can provide a method:
public String getTitle() {
    return title;
}
that returns the value of title. By convention, the name of an accessor method for a variable is obtained by capitalizing the name of variable and adding "get" in front of the name. So, for the variable title, we get an accessor method named "get" + "Title", or getTitle(). Because of this naming convention, accessor methods are more often referred to as getter methods. A getter method provides "read access" to a variable.
You might also want to allow "write access" to a private variable. That is, you might want to make it possible for other classes to specify a new value for the variable. This is done with a setter method. (If you don't like simple, Anglo-Saxon words, you can use the fancier term mutator method.) The name of a setter method should consist of "set" followed by a capitalized copy of the variable's name, and it should have a parameter with the same type as the variable. A setter method for the variable title could be written
public void setTitle( String newTitle ) {
   title = newTitle;
}

It is actually very common to provide both a getter and a setter method for a private member variable. Since this allows other classes both to see and to change the value of the variable, you might wonder why not just make the variable public? The reason is that getters and setters are not restricted to simply reading and writing the variable's value. In fact, they can take any action at all. For example, a getter method might keep track of the number of times that the variable has been accessed:
public String getTitle() {
    titleAccessCount++;  // Increment member variable titleAccessCount.
    return title;
}
and a setter method might check that the value that is being assigned to the variable is legal:
public void setTitle( String newTitle ) {
   if ( newTitle == null )   // Don't allow null strings as titles!
      title = "(Untitled)";  // Use an appropriate default value instead.
   else
      title = newTitle;
}
Even if you can't think of any extra chores to do in a getter or setter method, you might change your mind in the future when you redesign and improve your class. If you've used a getter and setter from the beginning, you can make the modification to your class without affecting any of the classes that use your class. The private member variable is not part of the public interface of your class; only the public getter and setter methods are. If you haven't used get and set from the beginning, you'll have to contact everyone who uses your class and tell them, "Sorry guys, you'll have to track down every use that you've made of this variable and change your code to use my new get and set methods instead."
A couple of final notes: Some advanced aspects of Java rely on the naming convention for getter and setter methods, so it's a good idea to follow the convention rigorously. And though I've been talking about using getter and setter methods for a variable, you can define get and set methods even if there is no variable. A getter and/or setter method defines a property of the class, that might or might not correspond to a variable. For example, if a class includes a public void instance method with signature setValue(double), then the class has a "property" named value of type double, and it has this property whether or not the class has a member variable named value.

Chitika