One of the largest realities of programming J2ME applications in my experience is the MIDlet size restrictions that are imposed. There is an overhead to every Java class you have in your MIDlet. This applies to inner classes and normal classes. It doesn't make any difference to go normal class compared to inner-class. We noticed about a 600 byte overhead for a class (uncompressed). They add up very quickly.
We wrote a flash player in BREW and J2ME. Without function pointers in J2ME we used separate classes for our action and condition handling. It was great except that the MIDlet size was 300Kb. We eventually got it down to 50Kb (and were able to deploy) but this involved things that would make Mark freak out. With a tear in my eye, I washed my hands every night when I'd finished.
We gained a large benefit by reducing the number of classes we had. We also noticed that the classes seemed to hit a sweet spot with the JAR compression when they got above 32Kb (uncompressed). After working with a lot of PNGs I realised this was due to the 32Kb sliding window that the ZIP algorithm uses for compression. When you hit 32Kb for a class file (after obfuscation - we used DashO) you maximise the benefit from the sliding window. The benefit is linear thereafter.
Our technique we used for this is was to assimilate classes into a parent class for where there was a 1:1 ratio. They we just prefixed the method names with the old class names. You get very big java files but it's still vaguely manageable if you originated from an OO design. Also, we did some extremely nasty things by assimilating children classes (where there was a 1:m relationship) by moving the methods up to the parent, passing in the object to the method call and turning the fields for the children objects into Object arrays.
For example our linked list class was assimilated by the MIDlet class. A list was an Object[]. A List node was an Object[]. The lists enqueue method was implemented by the MIDlet by passing in the list "object" as a parameter. Very nasty - lots of casting - you've got to write down how each object breaks down.
I love writing J2SE and
J2EE code. Writing J2ME code is a different kettle of fish in my opinion.
PK