Make defensive copies on both entry and exit, while keeping the supplied The private stored dimensions have no aliases exposed to the caller and are never changed. Mutating the constructor argument affects only the caller's object; mutating a returned
Dimension class unchanged:class Frame(d: Dimension) {
require(d != null)
private val saved = new Dimension(d.width, d.height)
private val savedArea = saved.width * saved.height
def area: Int = savedArea
def dimension: Dimension = new Dimension(saved.width, saved.height)
def isPortrait: Boolean = saved.height >= saved.width
}Dimension affects only a fresh copy. Consequently the stored area is calculated once and stays equal to the stored dimensions' product. This defensive copying is sufficient because Dimension contains only primitive fields; a more deeply nested mutable structure could require a deep copy or an immutable representation.The multiplication above deliberately retains the supplied class's
Int arithmetic and accessor type. If an exact mathematical area outside that range is required, compute once with saved.width.toLong * saved.height.toLong and expose Long instead; avoiding aliases and avoiding integer overflow are separate concerns. Articles by others on the same topic
There are currently no matching articles.