wood burning stoves 2.0*
The moose likes Performance and the fly likes Custom Events, Listeners, & Performance Big Moose Saloon
  Search | Java FAQ | Recent Topics | Flagged Topics | Hot Topics | Zero Replies
Register / Login


JavaRanch » Java Forums » Java » Performance
Bookmark "Custom Events, Listeners, & Performance" Watch "Custom Events, Listeners, & Performance" New topic
Author

Custom Events, Listeners, & Performance

Joseph Macer
Ranch Hand

Joined: Apr 20, 2008
Posts: 63
Hello,

I'm building a collaborative Java project that has a lot of components, and each of the components needs to tell other parts to do things. For example, if the networked class Client gets a message from the server, it needs to tell UserInterface to display the message, etc.

What I am doing right now is building custom events and listener interfaces for every action that needs to be communicated. This is nice, because I can tell other coders to add

to their class declaration, and put any code inside the function

that is supposed to happen whenever the get a public message.

Like I said, this is good because it segments our code - I can rewrite my entire client/server architecture and commit it to our repository, and everything works fine because the events are still passed the same way. But it is also a pain, because you end up with a lot of semi-useless classes:


So what I'm wondering is: is this the right way to go about it? Is there another way to have classes that are unaware of each other communicate? Is this efficient?

Thanks for any responses
[ May 25, 2008: Message edited by: Joseph Macer ]
William Brogden
Author and all-around good cowpoke
Rancher

Joined: Mar 22, 2000
Posts: 12792
    
    5
The Observer interface and Observable class have been in the java.util package since Java version 1.0 - probably not what you want.

I can't see any reason to have so many separate classes, why not one class of event and one listener interface. Stick the specific details in the general event class with a Map collection and a int type variable. Listeners can examine the type and quickly determine if they need to do anything.

Bill
steve souza
Ranch Hand

Joined: Jun 26, 2002
Posts: 861
I agree with Bill. You should look at some other projects that use events to see how they are handled too. Quartz timer API, and log4j come to mind.

Typical java style is to not use underscores in method names.
get_PublicMessage should be getPublicMessage.


http://www.jamonapi.com/ - a fast, free open source performance tuning api.
JavaRanch Performance FAQ
Ilja Preuss
author
Sheriff

Joined: Jul 11, 2001
Posts: 14112
Originally posted by William Brogden:
I can't see any reason to have so many separate classes, why not one class of event and one listener interface. Stick the specific details in the general event class with a Map collection and a int type variable. Listeners can examine the type and quickly determine if they need to do anything.


Well, one of the reasons to have so many classes would be that it makes the code more expressive. A quite important reason to me, actually. Using a Map collection and int type variable sounds a lot more brittle and complicated to me.


The soul is dyed the color of its thoughts. Think only on those things that are in line with your principles and can bear the light of day. The content of your character is your choice. Day by day, what you do is who you become. Your integrity is your destiny - it is the light that guides your way. - Heraclitus
Joseph Macer
Ranch Hand

Joined: Apr 20, 2008
Posts: 63
Thank you for the responses

Originally posted by William Brogden:
The Observer interface and Observable class have been in the java.util package since Java version 1.0 - probably not what you want.

Slightly confused here - is this what I am using, or are you specifically telling me NOT to seek Observers as an alternative? I don't implement "Observable"...

Originally posted by William Brogden:
I can't see any reason to have so many separate classes, why not one class of event and one listener interface. Stick the specific details in the general event class with a Map collection and a int type variable. Listeners can examine the type and quickly determine if they need to do anything.

Well, the reason I fire different types of events is so the "if (a) else if (b)....." statements only have to run (and be coded) at one point in the interpretation - that's why I have events for Public and Private messages. Otherwise you'd be running the same code twice, once when fired and once when received? (EDIT - clarification, you'd be having logic run twice anyway, not necessarily the same if/else code. My point is it's redundant) Perhaps I'm missing your intended point.
[ May 27, 2008: Message edited by: Joseph Macer ]
William Brogden
Author and all-around good cowpoke
Rancher

Joined: Mar 22, 2000
Posts: 12792
    
    5
1. the only reason I brought up Observer is to suggest you might want to look at the source code or at examples where it is used.

2. the only code that has to run on the side of a listener is:

if( event.type != MY_TYPE ) return ;
// otherwise process the event

3. on the event firing side you will obviously have custom code that gathers the data for that particular kind of event in a Map and creates the event like this:
MyEvent evt = new MyEvent( THE_EVENT_TYPE, themap );
callListeners( evt );
or possibly hand the event to another thread so the event creating Thread can continue working - waiting on listeners is a potential bottleneck.

4. If the interested parties are distributed over more than one JVM this might be a job for Java Message Service coordination.

Bill
[ May 28, 2008: Message edited by: William Brogden ]
steve souza
Ranch Hand

Joined: Jun 26, 2002
Posts: 861
I can't see any reason to have so many separate classes, why not one class of event and one listener interface. Stick the specific details in the general event class with a Map collection and a int type variable. Listeners can examine the type and quickly determine if they need to do anything.


Well, one of the reasons to have so many classes would be that it makes the code more expressive. A quite important reason to me, actually.


I believe both have their uses, and without knowing the intent of the code it is difficult to say which approach is better. Both approaches should be in our arsenal. I think it is important to pass a generic data structure like a hash map when you are developing a toolkit or framework that may be used in ways you can't determine at design time.

For example suppose a client to your framework wants to take your generic listener and add to it the ability to start a transaction and pass the state of the transaction to other listeners in a chain. Your original design didn't take this into account. A flexible argument passing approach would be useful in this case. Another example would be if a Monitor/Probe object was passed to every event listener and this was not part of the original design. If it is important to have such flexibility in your design then passing a generic data type is useful (you could also have a tag interface and type cast). If it isn't important than I would go for the type safety and clearer intent.
[ May 28, 2008: Message edited by: steve souza ]
Joseph Macer
Ranch Hand

Joined: Apr 20, 2008
Posts: 63
Well, I like having extremely simple functions, but future flexibility may be important as well, I hadn't considered it. It would also cut down on the listeners I'd have to implement (1 instead of n).

I think I will talk with my team to decide which approach to use. Thanks for the options and the pros/cons, guys
Ilja Preuss
author
Sheriff

Joined: Jul 11, 2001
Posts: 14112
I agree that there is a balance. Take the PropertyChangeEvent, for example - you wouldn't want to introduce a new event type for each property that might change. That is, *sometimes* you actually will.

To me, it basically comes down to the number of special cases that need to be introduced. Before I have an if statement in every single listener/observer I implement, I'd rather look very closely at how much work it would be to fire more specific events.

As an aside, you don't always need to introduce a new event type to have more specific events. You can also reuse event types for different events:

addPropertyChangeListener(String propertyName, PropertyChangeListener listener)

or

addFooChangeListener(ChangeListener listener)
addBarChangeListener(ChangeListener listener)
 
GeeCON Prague 2014
 
subject: Custom Events, Listeners, & Performance