In the following, I want EventHandler to handle EventA one way, EventB another way, and any other Events (EventC, EventD) yet another way. EventReceiver receives only a reference to an Event and calls EventHandler.handle(). The version that always gets called, of course, is EventHandler.handle(Event event).
Without using instanceOf, is there a way to polymorphically dispatch (perhaps via another method in EventHandler or generics) to the appropriate handle method?
class EventA extends Event {
}
class EventB extends Event {
}
class EventC extends Event {
}
class EventD extends Event {
}
class EventHandler {
    void handle(EventA event) {
       System.out.println("Handling EventA");
    }
    void handle(EventB event) {
       System.out.println("Handling EventB");
    }
    void handle(Event event) {
       System.out.println("Handling Event");
    }
}
class EventReceiver {
    private EventHandler handler;
    void receive(Event event) {
        handler.handle(event);
    }
}    
                A Dispatcher is used to build an application by aggregating several services. The dispatcher maintains a registry of Service objects. A Service is categorized by the type of processing it performs: A pre-processing service pre-processes input data for the command being processed.
Dynamic method dispatch is the mechanism in which a call to an overridden method is resolved at run time instead of compile time. This is an important concept because of how Java implements run-time polymorphism.
Dynamic method dispatch is the mechanism by which a call to an overridden method is resolved at run time, rather than compile time.
Double dispatch is a technical term to describe the process of choosing the method to invoke based both on receiver and argument types. A lot of developers often confuse double dispatch with Strategy Pattern. Java doesn't support double dispatch, but there are techniques we can employ to overcome this limitation.
Sounds like a case for applying (a variant of) the Visitor pattern. (In mainstream OO languages such as C++, C# and Java, methods are single dispatch, i.e. can only be polymorphic on one type at a time. Visitor allows one to implement double dispatch.)
This however requires that you be able to modify the Event classes as well, and creates a dependency from Events to (a base interface of) EventHandler.
class EventA extends Event {
  public handleBy(EventHandler eh) {
    eh.handleEventA(this);
  }
}
class EventB extends Event {
  public handleBy(EventHandler eh) {
    eh.handleEventB(this);
  }
}
class EventHandler {
    void handleEventA(EventA event) {
       System.out.println("Handling EventA");
    }
    void handleEventB(EventB event) {
       System.out.println("Handling EventB");
    }
    void handle(Event event) {
       event.handleBy(this);
    }
}
                        This is a use case for double-dispatch, no (which as one may indeed know is either called Visitor) ? I'll implement your example for EventA only
class Event {
    /**
     * Will do some type escalation
     */
    void handleWith(EventHandler care) {
        care.handle(this);
    }
}
class EventA extends Event {
    /**
     * As event is EventA, this implementation is called, with its correct type forced by the cast
     */
    void handleWith(EventHandler care) {
        care.handle((EventA) this);
    }
}
class EventHandler {
    /**
     * Finally comes here
     */
    void handle(EventA event) {
       System.out.println("Handling EventA");
    }
    void handle(EventB event) {
       System.out.println("Handling EventB");
    }
    void handle(Event event) {
       System.out.println("Handling Event");
    }
    /**
     * Go here first and dispatch call to Event class
     */
    void doHandle(Event event) {
        event.handleWith(this);
    }
}
class EventReceiver {
    private EventHandler handler;
    void receive(Event event) {
        handler.doHandle(event);
    }
}    
                        If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With