Scott's Rule of Reuse # 1:
ALL VARIABLE DATA MUST BE PRIVATE
NOTE: There is only one exception to this rule: final static variables (aka class constants). Otherwise, there are to be no exceptions to Scott's rule #1. Ever.
The reason for this is that a class must be in total control of its state. If someone makes a change, the class must have a chance to know about it. If we leave variables non-private, some other class can change our state w/o us knowing.
The only way variables are to be changed is via methods defined in the class, preferably a setXXX() method. Initially the set method is simply changing the value. However, later on, we can add code to the set method to
- add validation to ensure the value is acceptable
- fire events to tell others that the value has changed
- update other state when the value changes
- log that the value has changed
If the variable is non-private, the set method might not be called when it changes, so we cannot guarantee to be able to fire a property change, validate, etc.
All Data Must Be Private!
I could go on and on about this forever, but I'll try to keep it brief: All data defined in a class must be private!
I may sound a bit like an "OO-purist" when I say this, but I view this from a practical standpoint, having been burned by not doing it...
Making data (by data I mean class and instance variables) non-private allows another class to change their values without the owner of that data knowing about the change. If the owner doesn't know about the change:
- the owner has no control over the value; it could be outside the intended range of the data
- the owner cannot know the value has change, and cannot respond if needed
- the owner cannot tell others that the value has changed
- the owner cannot allow others to veto the change
On top of these problems, if you ever decide to change your code to allow other classes to listen for changes, or restrict bounds on a variable, you would need to find every reference to the data and change it. This can be very painful if the class were a public library that many people had used in their own code.
Even worse, you cannot change the implementation of the data without changing the users of that data. For example, suppose you had an integer instance variable to keep track of some ID for a list node. Perhaps you had done some research and decided that the memory cost of keeping that ID was more expensive than recomputing it the few times it was needed. If ID were only available via an accessor, all you would need to do to affect the change is to remove the instance variable and change the getID accessor to compute the ID and return it. Far simpler than creating the getID accessor and going back and changing every reference to x.id...
Privacy is the key to true encapsulation. All manipulation of an object's state must be done by the object itself!
Once you use accessors to read/write class/instance data, that data is instantly available as a JavaBean property!