What's good practice for accessing class attributes in class methods?
I always wonder about the best way to access a class attribute from a class method in Java.
Could you quickly convince me that one of the three solutions below (or completely different: P) is good practice?
public class Test {
String a;
public String getA(){
return this.a;
}
public setA(String a){
this.a = a;
}
// Using Getter
public void display(){
// Solution 1
System.out.println(this.a);
// Solution 2
System.out.println(getA());
// Solution 3
System.out.println(this.getA());
}
// Using Setter
public void myMethod(String b, String c){
// Solution 1
this.a = b + c;
// Solution 2
setA(b + c);
// Solution 3
this.setA(b + c);
}
}
a source to share
It totally depends on what the getters and setters are doing. If they do more than just get and set the value (which must be explicitly documented in the Javadoc method), then it really matters how you choose inside the class. But if they are pure Javabeans like getters / setters, then I would prefer to access the variable directly either with a
or this.a
depending on whether there is a local variable in scope with that name.
Personally, I would just leave getters and setters "clean" according to the Javabean spec and add another getter or setter with a self-explanatory method name whenever I wanted to do more than just get / set a value. For instance. getAndIncrement()
, getAsString()
, setAsInt(String)
Etc.
A matter of taste. It doesn't hurt if you agree with it at the time of your encoding.
a source to share
If you need to create any validation in the future, you need a setter / getter. When you make a variable visible, you slow down the encapsulation of the class. In theory, this means that your code is not object oriented: P, but in practice you lose the ability to do a lot of code refactoring. For example, retrieving an interface. And for this call, I consider it unnecessary, but that's just me :)
a source to share
I use getters and setters in the class if there is more logic that return this.value. This way I avoid duplication. Example:
...
public List<String> getList() {
if (this.list == null) {
this.list = new LinkedList<String>();
}
return this.list;
}
public int getListSize() {
return getList().size();
}
...
I always use "this" because it is easier for other users to read my code. There is no doubt that this.value is a class attribute, whereas a value can be either a local variable or a class attribute.
a source to share
Solution 2 or 3 is best practice as they provide field encapsulation. For example, what if the field 'a'
is the user's zip code and your application has a new requirement to always return the zip code as uppercase. With solutions 2 or 3, it becomes trivial. For instance.
private String postcode;
public String getPostcode()
{
return postcode;
}
becomes
private String postcode;
public String getPostcode()
{
return postcode != null? postcode.toUppercase() : null;
}
and you will only make the change in one place, not anywhere the field is available. Adding this
only depends on your personal style or project standards. I personally don't like this as it is unnecessary and just interferes with readability, but for others it makes the owner of the method / field clearer.
a source to share
Using getters and setters is the way to go.
- This is a common practice.
So other programmers are more likely to understand your code.
- It gives options to the author of the class in the future
Let's say you want someone to set it to null. Submit a member and you can never do it.
As far as usage goes this
- I try to use it this
consistently to make it clear to everyone who are members of the instance and who are local variables at all times, also helps to avoid accidental shadowing, but I think it's less important and more stylish.
Also - this.a
is a member of the instance (one per instance), not a member of the class (one per class, will be static). Another reason to use this
is to be clear.
a source to share
I would go with
System.out.println(getA());
and
setA(b + c);
for the simple reason that if you would like to change the way you access an attribute at all, or apply any restrictions on what you could set a variable to, you can simply change the getA or setA methods.
I don't like using this unless I need to explicitly distinguish between variables with the same name.
a source to share