Hi Tom, Thanks for your observation and your code proposal; always welcome.
I have some concerns that the caching of non-existing classes could be exploited and bloat the cache. Maybe we’d need to use WeakHashMap (and/or soft references) instead? > I'm not sure why BaseX tries to load our xqm as Java Modules, but what I > noticed is that Reflect.forName caches the positive case (i.e., the class is > found), but not the negative case (i.e., the class is not found). Sounds like an interesting finding; maybe there’s something we can optimize here. Could you possibly provide us a little self-contained example that demonstrates the behavior? Thanks in advance, Christian On Wed, Oct 17, 2018 at 9:53 AM Tom Rauchenwald (UNIFITS) <tom.rauchenw...@unifits.com> wrote: > > Hi BaseX-Team, > > > when profiling some of our tests i found that we spend some time in > Reflect.forName(). > > We have 2 xquery modules in the repo (we don't call java code directly). > > > I'm not sure why BaseX tries to load our xqm as Java Modules, but what I > noticed is that Reflect.forName caches the positive case (i.e., the class is > found), but not the negative case (i.e., the class is not found). > > I've changed the code to cache the negative case as well (see below), and > noticed an improvement of about 5 percent. > > Our tests create and query loads of small databases, so this is maybe quite > an artificial speedup. > > > I could provide a PR if this is a worthwhile improvement in your opinion (and > if I'm not missing something obvious). > > > We're still on BaseX 8.7.6 in case that matters, as far as I could see the > Code didn't change in BaseX 9. > > > Thanks, > > Tom > > > Code: > > > public static Class<?> forName(final String name) throws > ClassNotFoundException { > Class<?> c = CLASSES.get(name); > > if(c == null) { > if (CLASSES.containsKey(name)) { > throw new ClassNotFoundException(name); > } else { > try { > c = Class.forName(name); > } catch (ClassNotFoundException e) { > CLASSES.put(name, null); > throw e; > } > if (!Modifier.isPublic(c.getModifiers())) throw new > ClassNotFoundException(name); > CLASSES.put(name, c); > } > } > return c; > } >