#inline > -----Original Message----- > From: [EMAIL PROTECTED] > [mailto:[EMAIL PROTECTED]]On Behalf Of Ara > Abrahamian > Sent: 22. februar 2002 10:33 > To: [EMAIL PROTECTED]; [EMAIL PROTECTED] > Subject: RE: [Xdoclet-devel] xjavadoc optimisation+API essay > > > Excellent benchmark! > > > Here is the strategy: > > We can generate two versions of the parser. One JJTree based, needed > for > > doc > > mutation (XDoclet GUI and Reverse XDoclet) and one JavaCC based used > for > > XDoclet. XDoclet doesn't need to mutate the docs. We can use the same > > grammar, just decide whether we preprocess it with JJTree or not. We > > should > > preprocess the grammar file itself, to make sure the generated parsers > go > > into different packages. We can use XDoclet's ReplaceCopy task for > this. > > ;-)) > > Assuming that 80% of templates will generate new classes instead of > mutating an existing class we can definitely make it faster by not > instantiating jjtree AST objects. The best solution would be a runtime
I'm not following here. What kind of templates would want to *modify* existing sources? -Or more specifically: esisting sources' javadocs (cause that's the only thing you can modify with xjavadoc). > flag which determines whether jjtree is needed or not. I mean say > CompilationUnit() does the jjtree.openNodeScope/etc only if That would require editing the generated JavaParser, which is not a good idea. If we modify the grammar, the changes will be lost. It's better to generate two parsers from the same grammar; one jjtree based and one direct javacc. These will be in different packages. -But I don't understand why templates need to modify sources (and therefore use the jjtree parser). > XJavaDoc.isJJTreeNeeded==true. We can set this flag *per template*, so > if a template generates a new class then true, else false. I'm not sure > it's possible but it'd be cool. We just need to wrap those jjtree.blabla > calls in JavaParser with if(needed) statement. We won't need two > grammars and two set of parsers/etc in this case. Aslak, do you think > it's possible? > One grammar, two parsers. > > But this only removes the overhead of Node creation. We also need to > > reduce > > the creation of xjavadoc objects, and that's more tricky. I reread the > > flyweight pattern from GoF's Design Patterns, and I think that's a > good > > pattern to use. It's about sharing objects. We can start by > flyghweighting > > the XParameter class. We can make ParameterImpl a singleton, and each > > MethodImpl can contain a two dimensional int array representing > pointer to > > a > > huge StringBuffer (which is a member of ParameterImpl) to extract the > type > > and name members. This way we don't have to instantiate a lot of heavy > > String objects, we just append to the StringBuffer as we parse, and > > maintain > > these int arrays. I want to start with ParameterImpl, because this is > the > > class that will probably be instantiated the most. > > Flyweight is the way to go. I implemented a simple form of it with the > XJavaDoc.getXClass method, so all parameters/return-types/classes are > lazy loaded and the XClass pointer is null until it's accessed actually. The flyweight pattern has nothing to do with lazy loading. It's about storing extrinsic state as lightweight members (ints) and passing that state to a shared object before accessing it. See http://www.enteract.com/%7Ebradapp/javapats.html#Flyweight > But we can enhance it, and as you said before just store the qualified > name of a class instead of the XClass object and so on. I would love to That's already done. The lazy loading is done in XJavaDoc.getXClass(String,boolean). This method returns a proxy class if the boolean is true. The only class that ever calls XJavaDoc.getXClass(String,boolean) with true is ProxyClass. This means that when you do a superclass() on a class, you'll get an instance of ProxyClass. You can call qualifiedName() on that instance without anything happening, but if you try to call any other method, the ProxyClass will ask for the real instance (the subject) by calling XJavaDoc.getXClass(String,boolean) with false. This mix of lazy loading and proxy is quite efficient, but not enough. I guess what you're talking about is to lazy-instantiate the Xxxx[] arrays. That can be done too. > see a very low overhead XMethod object (or lazy loading it altogether!), > most of the methods are not accessed at all. And it's even more true for > parameters. > Do you think you could add some benchmarking code to xdoclet so we get som metrics about what's really accessed and how often? The samples are good to use as a basis. > And remember the XJavaDoc.getXClass is way more significant than you > think. Our xjavadoc parser may be *slower in parsing a single class* but > because we don't load/parse all classes like doclet our approach should > be tens of times faster! Specially when you rerun xdoclet on an already > built output, and you only changed a single ejb after the previous > build. Only that single class and its superclasses are scanned. > True. XJavaDoc should only be instantiated with setDir, _not_ with setFiles. If dir is known, we can load classes on demand. > > I've also been thinking abot xdoclet's API. The main difference from > > javadoc > > in the current API is that XProgramElement has-an XDoc, whereas > > ProgramElementDoc is-a Doc. Containment versus inheritance. I did it > that > > way when I designed it because I thought it was better design. I still > > think > > it is, but we might get some benefits from being compatible with > javadoc. > > The most signinificant one being the ability to use all the doclets > out > > there (including the standard HTML API doclet). An other benefit is > that > > XDoclet's migration from javadoc to xjavadoc will be a no-brainer. > > I think it's ok. doc() is unintuitive and I don't think it's a major > problem in our migration. It's used in getTagsByName/etc not scattered > in code deeply. > > The Type class is also not present in our hierarchy but I also think > this one is a good refinement of the doclet api. Type is used for > primitive types (not everything is a class). The way Type is used in > Sun's doclet api is wrong imho. Keep it as is. There's no MemeberClass > either, and this one is also fine. The hierarchy we have currently is ok > imho. > Good, so we'll not try to be compatible with the javadoc API. Being able to use javadoc doclets is not a big issue, and if you think the xdoclet migration with the current xjavadoc API is ok, then let's forget about javadoc API. > > public interface XClass extends ClassDoc { > > XClass superclassx(); > > } > > No no! Why? Bad idea! If migration proves to me very hard we'll start > adopting these kinds of adapting/decorating strategies. > > For the moment: concentrate on completing the feature set, concentrate > on laying the ground for a generic optimization system. If we're going Well, here are som more benchmarking info: [xjavadoc] ParameterImpl instances: 1118 [xjavadoc] MethodImpl instances: 1257 [xjavadoc] ConstructorImpl instances: 0 [xjavadoc] SimpleNode instances: 302143 I'll take a look at making flyweight out of ParameterImpl now.... > to store the full class name only and no XClass object till needed then > we should adopt this strategy from the beginning. > > Cheers, > Ara. > Ciao, Aslak > > _________________________________________________________ > Do You Yahoo!? > Get your free @yahoo.com address at http://mail.yahoo.com > > > _______________________________________________ > Xdoclet-devel mailing list > [EMAIL PROTECTED] > https://lists.sourceforge.net/lists/listinfo/xdoclet-devel _______________________________________________ Xdoclet-devel mailing list [EMAIL PROTECTED] https://lists.sourceforge.net/lists/listinfo/xdoclet-devel
