Gilberto
Gilberto

Reputation: 13

Java Reflection: the fast way to retrieve value from property

I would like to use the fastest way to retrieve value from a property.

Should I use:

public Object getValue(Object obj, Field field) {
    field.setAccessible(true);
    return field.get(obj);
}

or should I use:

public Object getValue(Object obj, Field field) throws Exception {
    StringBuilder methodName = new StringBuilder();
    methodName.append("get");
    methodName.append(field.getName().substring(0, 1).toUpperCase());
    methodName.append(field.getName().substring(1, field.getName().length()));
    for (Method method : methods) {
        if (method.getName().equals(methodName.toString())) {
            return method.invoke(obj);
        }
    }
}

or should I use:

public Object getValue(Object obj, Field field) throws Throwable {
        MethodHandles.Lookup lookup = MethodHandles.lookup();
        StringBuilder methodName = new StringBuilder();
        methodName.append("get");
        methodName.append(field.getName().substring(0, 1).toUpperCase());
        methodName.append(field.getName().substring(1, field.getName().length()));
        for (Method method : methods) {
            if (method.getName().equals(methodName.toString())) {
                MethodHandle mh = lookup.findVirtual(obj.getClass(), methodName.toString(), MethodType.methodType(field.getType()));

                return mh.invoke(obj);
            }
        }
    }

Thanks in advance.

Upvotes: 0

Views: 1822

Answers (2)

Mahendra Kapadne
Mahendra Kapadne

Reputation: 426

If you are using Java 8 then

  1. If you want use run reflection then you should go thought LambdaMetaFactory which gives approx equal performance as of direct method call [faster-alternatives-to-javas-reflection]

  2. If you want to make code configurable and but configuration doesn’t change at run time. Then one should go with AnnotationProcessor processor to generate code. It makes perfect combination of configuration, performance, maintenance & ease of use.

[annotation processing] [annotation Processing with maven]

Upvotes: 1

GhostCat
GhostCat

Reputation: 140427

There are different levels in there:

  • A field access is a field access. A method that access the field will ... access the field, too. Just with much more overhead.
  • You have to maintain your code over time.

The first point suggests that a "straight forward" field access should always be faster (especially given the fact that this method is pretty short - and the JIT is much better at inlining short methods). Leading to the second point: simply ask yourself which of the three methods is the easiest to read and understand.

The key thing is that reflection calls are expensive. The method handle concept is intended to improve that cost (by avoiding the checks that a method call using reflection is undergoing each time). So if you are really interested in finding the "optimal" code, then the answer might be framed around a solution that computes a method handle once, to then be re-used for subsequent calls. There is absolutely no point in instantiating a method handle just to make a single call. Nothing to be gained from that - method handles are "cheaper" than ordinary reflection only when you repeatedly use the method handle to make calls.

Of course, the real answer is: you step back, you learn how to correctly benchmark java code, and then you do a bit of measuring within your context, environment - your data, your code. To then draw your final conclusion. And I also agree with the comment given by spi - if performance is crucial to you, then reflection is (more or less) a no go.

Upvotes: 2

Related Questions