My COMP303 course notes. Available in Markdown. A sample of my notes for Module 3 is available below.
An abstract state is a state that impact how an object would be used. For example appending to a linked list when it is empty vs when it has more than 1 element
Use Optional.empty()
instead of null
to help avoid nullpointer exceptions.
Goal: avoid null
and Optional
, but still avoid nullpointer exceptions.
Create an implementation of an interface that represents a null class instead of directly passing null
so that the code doesn't break when null isn't checked.
See NullObject.java
Goal: Avoid redundancy when storing data
Create an array that contains the values, then newly created object simply need to keep track of the index of the value, saving memory. 4 steps to realize this:
- private constructor
- static initializing fields that creates the flyweight objects
- static flyweight store (ex: array) that stores all the flyweight objects
- static access method that returns the flyweigth objects according to a key
See Flyweight.java
Goal: ensure only 1 instance of class (ex: database access, aggregation of states)
This is similar to flyweight, but in this case we only want 1 instance, so no key, and the store is a variable that points to the instance. 3 steps to realize this:
- private constructor
- variable that points to the instance
- static access method
See Singleton.java
Create an anonymous class from an interface (ex: using Comparator<T>
) without defining it by using return new Interface() {}
See Anonymous.java
null
always return false- Use
==
to check if same instance. If so returntrue
- Use
instanceof
to check if same type. If not returnfalse
- Cast to correct type
- For each significant field, check that they are equal to eachother
float
: useFloat.compare(float, float)
double
: useDouble.compare(double, double)
- Primitive fields: use
==
- Others:
Objects.equals(Object, Object)
Additionally, use @Override
Improper implementation of hashcode will prevent proper functioning in collections like hashmap or hashset. Always test whether 2 equal instances have same hash code.
Requirements:
- must consistently return the same value when called on the same object if no info is modified
- if two objects are equal according to
equals()
, they must have the same hashcode - two objects that are not equal don't need to have distinct hashcode, but that might improve performance
How to create good hashcode:
- select random non-zero constant into int
result
(ex: 17) - for each field:
- compute hashcode
c
- Combine hashcode
c
intoresult
:result = 31 * result + c
- compute hashcode
- return result