@Documented @Retention(value=RUNTIME) @Target(value=TYPE) public @interface ReferenceObject
Thread and
Object.
This annotation is related, but not entirely synonymous, with an entity object in the software design literature. A reference object is a lower-level concept that uses the reference to the object in the heap as its identity. While an entity object could be implemented in Java using a reference object, it could also use an id field or some other mechanism. Therefore, all reference objects are entity objects, but not vice versa.
All enum type declarations are reference objects simply due the
restrictions imposed by the Java programming language. They are treated as if
they were annotated with @ReferenceObject—but no
user-supplied annotation is needed, it is implied. It is a modeling problem
for any enum type to be annotated as either an
@ReferenceObject or a @ValueObject.
This annotation is currently verified, but not defined, by
restricting which Annotation.equals(Object) and Annotation.hashCode() methods
instances invoke at runtime. All reference objects must invoke these
methods on Object—neither they nor their parent types
can override the Annotation.equals(Object) and Annotation.hashCode() methods.
Equality comparisons on reference objects are not checked because it is
possible to use either reference equality comparisons (==) or
Annotation.equals(Object) comparisons. This is because the
Object.equals(Object) method is implemented using
== as shown below.
public boolean equals(Object obj) {
return (this == obj);
}
A type may not be annotated with both @ReferenceObject and
@ValueObject.
Subtypes of a type other than Object annotated with
@ReferenceObject must also be explicitly annotated
@ReferenceObject. It is a modeling error if they are not.
Note that it is not a modeling error to have one or more types in the
type hierarchy between Object and the type annotated as a
@ReferenceObject which are not annotated as a
@ReferenceObject (this is to avoid unnecessary annotation
on the Java libraries).
An interface may be annotated with @ReferenceObject. In
this case all subtypes must also be explicitly annotated with
@ReferenceObject. It is a modeling error if they are not.
In some cases this may be useful to allow comparisons with the interface type
using == while being sure that no implementing classes override
Annotation.equals(Object) and Annotation.hashCode() methods—which would
cause the comparisons using == to be possibly incorrect.
An annotation type declaration may not be annotated with
@ReferenceObject.
@ReferenceObject is determined by its reference in the
heap. Two distinct reference objects in the heap are never equal.
@ReferenceObject
public final class ServerProxy extends Thread {
...
}
Note that neither Thread or ServerProxey override
Annotation.equals(Object) and Annotation.hashCode() methods.
The Point class below would normally be annotated as a
@ValueObject. However, a Java implementation of the
Flyweight pattern must is used to allow it to use reference equality
semantics. This design pattern is described by Gamma, Helm, Johnson, and
Vlissides in Design Patterns: Elements of Reusable Object-Oriented
Software (Addison-Wesley 1995). Note that this code is likely to be
much slower than implementing Point as a value object.
@Immutable
@ReferenceObject
public final class Point {
private static final List<Point> INSTANCES = new ArrayList<Point>();
public static Point getOnlyInstance(int x, int y) {
for (Point p : INSTANCES) {
if (p.x == x && p.y == y)
return p;
}
Point result = new Point(x, y);
INSTANCES.add(result);
return result;
}
private Point(int x, int y) {
this.x = x;
this.y = y;
}
public Point(Point p) {
x = p.x;
y = p.y;
}
private final int x, y;
public int getX() {
return x;
}
public int getY() {
return y;
}
}
@annotate tag.
/**
* @annotate ReferenceObject
*/
public final class ServerProxy extends Thread {
...
}
Copyright © 2012 Surelogic, Inc.. All Rights Reserved.