import java.util.*; import org.aspectj.lang.annotation.*; class Blob {} public aspect TheBigOne extends ParentChildRelationship { public static void main(String []argv) { Blob a = new Blob(); Blob b = new Blob(); Blob c = new Blob(); Blob d = new Blob(); Blob e = new Blob(); // arrange as follows: A contains B,C,D and B contains E a.addChild(b); a.addChild(c); a.addChild(d); b.addChild(e); // now query the layout if (!e.getParent().equals(b)) throw new RuntimeException("why is E not parent of B? "+e.getParent()); if (!d.getParent().equals(a)) throw new RuntimeException("why is A not parent of D? "+d.getParent()); if (a.getChildren().size()!=3) throw new RuntimeException("A should have 3 children, not:"+a.getChildren().size()); } } abstract aspect ParentChildRelationship { interface ParentHasChildren{} interface ChildHasParent

{} declare parents: Parent implements ParentHasChildren; declare parents: Child implements ChildHasParent; public List ParentHasChildren.children = new ArrayList(); public P ChildHasParent

.parent; public List ParentHasChildren.getChildren() { return Collections.unmodifiableList(children); } public P ChildHasParent

.getParent() { return parent; } public void ChildHasParent.setParent(R parent) { this.parent = parent; ParentHasChildren phc = (ParentHasChildren)parent; if (phc.getChildren().contains(this)) phc.addChild(this); } public void ParentHasChildren.addChild(X child) { if (((ChildHasParent)child).parent != null) { ((ParentHasChildren)((ChildHasParent)child).parent).removeChild(child); } else { ((ChildHasParent)child).setParent((ParentHasChildren)this); } children.add(child); } public void ParentHasChildren.removeChild(Y child) { if (children.remove(child)) { ((ChildHasParent)child).parent = null; } } }