Encapsulation
A well-designed component hides all its implementation details, cleanly separating its API from its implementation. Components then communicate only through their APIs and are oblivious to each others’ inner workings. This concept, known as information hiding or encapsulation, is a fundamental tenet of software design. The advantages of encapsulation are as follows:
- Speeds up the system development as components can be developed in parallel
- Enables effective performance tuning. Components can be optimized separately without affecting the others
- Increases software reuse as components aren’t tightly coupled
- Decrease the risk in building large systems, improves resilience
Make each class or member as inaccessible as possible.
Access levels in classes and interfaces
- For top-level (non-nested) classes and interfaces, there are only two possible access levels: package-private and public.
- If a package-private top-level class or interface is used by only one class, consider making the top-level class a private static nested class of the sole class that uses it
Access levels in members (fields, methods, nested classes, and nested interfaces)
Modifier | Class | Package | Subclass | World |
---|---|---|---|---|
public | Y | Y | Y | Y |
protected | Y | Y | Y | N |
package-private (no modifier) | Y | Y | N | N |
private | Y | N | N | N |
Ensure that objects referenced by public static final fields are immutable
// Problem: Potential security hole! Clients will be able to modify the contents of the array
public static final Thing[] VALUES = { ... };
// Solution 1: Make the array private and add a public immutable list
private static final Integer[] PRIVATE_VALUES = { ... };
public static final List <Integer> VALUES = Collections.unmodifiableList( Arrays.asList( PRIVATE_VALUES));
// Solution 2: Make the array private and create a public static final function that returns a copy an array
private static final Integer[] PRIVATE_VALUES = { ... };
public static final Integer[] getValues() {
return PRIVATE_VALUES.clone();
}