/* My second AspectJ program This time we'll try to impose a stricter level of protection than just public, private, or protected. */ class rational { private int n, d; public rational(int n0, int d0) { n = n0; d = d0; } //rational equality public boolean eq(rational r) { return (n*r.d) == (d*r.n); } public void inc() { n +=d; } public String toString() { return n+"/"+d; } } aspect protector { // prevent zero denominator: (new picks out constructor) before(int n,int d) : call(rational.new(int,int)) && args(n,d) { if (d==0) throw new Error("zero denominator"); } // enforce a stronger form of "private" - similar to Scheme/Eiffel /* pointcut access() : get(int rational.n) || get(int rational.d) || set(int rational.n) || set(int rational.d); */ // using wildcards: pointcut access() : get(* rational.*) || set(* rational.*); before(rational a, rational b) : access() && this(a) && target(b) { if (a!=b) throw new Error("too private"); } } public class asecond { public static void main(String[] args) { rational r1, r2; r1 = new rational(1,2); r2 = new rational(2,4); r1.inc(); // ok System.out.println(r1.eq(r2)); } } /* In this program, the first advice can be duplicated inside the constructor - so one can think of it as an add-on. The only benefit is that the original code need not be touched (shouldn't it be though?). The second (and related third) advice is clearly doing something different. Technically, one can also put the explicit check in the eq file - but the point is that the program may NOT. In which case, we can enforce a stronger level of protection just be compiling the program with the protector aspect. */