I need some help understanding what the author is trying to demo.
The output is : other operation 1 callee1 2 callee1 3 callee1 4 callee1
I discovered that commenting out <incr()> in the body of Closure doesn't change the results.
Here's the authors comments: quote: Callee2 inherits from MyIncrement which already has a different increment() method which does something unrelated to that which is expected by the Incrementable interface. When MyIncrement is inherited into Callee2, increment() can't be overriden for use by Incrementable, so you're forced to provide a separate implementation usin an inner class. Also note that when you create an inner class you do not add to or modify the interface of the outer class. Notice that everything except getCallbackReference() is Callee2 is private. To allow any connection to the outside world, the interface Incrementable is essential. Here you can see how interfaces allow for a complete separation of interface from implementation. Inner class Closure simply implements Incrementable to provide a hook back into Callee2-but a safe hook. Whoever gets theIncrementable reference can, of course, only call increment() and has no other ablitities( unlike a pointer, which would allow you to run wild). Caller takes an Incrementable reference in its constructor (although the capturing of the callback reference could happen at any time( and then , somethime latter, uses the reference to "call back" into the Callee class end quote
It seems to me that some how I'm not sure how but it seems Closure's increment() is somehow forced (by what mechanism I'm not sure) to use Callee1's increment(). If this is correct can you elaborate at on on this.
I don't follow the authors' comment:< The inner class Closure simply implements Incrementable to provide a hook back into Callee2 > I see this as a hook back into Callee1 from what I see?
thank you craig
interface Incrementable{ void increment(); }
class Callee1 implements Incrementable { private int i= 0; public void increment() { i++; System.out.print(i + " "); System.out.println("Callee1 increment()"); } }
class MyIncrement { public void increment() { System.out.println("Other operation"); } public static void f(MyIncrement mi){ mi.increment(); } }
class Callee2 extends MyIncrement { private int i= 0; private void incr() { i++; System.out.print(i + " "); System.out.println("Callee2 increment()"); } private class Closure implements Incrementable { public void increment() { //incr(); } } Incrementable getCallbackReference() { return new Closure() ; } }
class Caller { private Incrementable callbackReference; Caller(Incrementable cbh) { callbackReference = cbh; } void go () { callbackReference.increment(); } }
public class Callbacks {
public static void main(String[] args) { Callee1 c1 = new Callee1(); Callee2 c2 = new Callee2 (); MyIncrement.f(c2); Caller caller1 = new Caller(c1); Caller caller2 = new Caller(c1); caller1.go (); caller1.go(); caller2.go(); caller2.go(); } }