In Java, is there a performance difference between a field reference via a getter versus a variable?

Are there any differences between execution

Field field = something.getSomethingElse().getField(); if (field == 0) { //do something } somelist.add(field); 

vs

 if (something.getSomethingElse().getField() == 0) { //do something } somelist.add(something.getSomethingElse().getField()); 

Are the links to the field using getters with performance limitations, or does it match the reference to the assigned variable? I understand that this variable is just a reference to memory space, so a getter should just be another way to get in that memory space.

Please note that this is an academic question (the school is just curious), not a practical one.

+4
source share
9 answers

Assuming getSomethingElse() is defined as

 public SomethingElse getSomethingElse() { return this.somethingElse; } 

The difference in performance will be minimal (or zero if it is included). However, in real life you can’t always be sure that it’s the matter - maybe some kind of processing happens behind the scenes (not necessarily in the object itself, but, say, through the AOP proxy). So storing the result in a variable for repeated access might be a good idea.

+7
source

This is minor damage. Do not worry about it too much or you will become a victim of premature optimization. If your application is slow, this is not the reason.

+11
source

There is a difference in that accessing variables through getters results in a method call. The JVM may be able to optimize the method call in some circumstances, but it is a method call.

However, if the biggest bottleneck or performance issue in your code is the overhead of access methods, I would say that you have nothing to worry about.

+5
source

There is a performance penalty (which can be so small that it is negligible). However, the JVM can embed this and all calls to improve performance.

It would be better if you left the second way.

+4
source

Not if you have a good JVM, like Sun's HotSpot. It will embed and compile (in native code) getters.

Using getters is usually a very good practice, as a protective measure and general hidden information.

+3
source

Please note that using Java to write Android applications is here: http://developer.android.com/training/articles/perf-tips.html#GettersSetters

In native languages ​​such as C ++, it is common practice to use getters (i = getCount ()) instead of directly accessing the field (i = mCount). This is a great habit for C ++ and is often practiced in another object such as C # and Java, since the compiler can usually embed access, and if you need to restrict or debug access to the field, you can add code at any time.

However, this is a bad idea for Android. Virtual method calls are more expensive, much more than a field search. It is reasonable to adhere to the general methods of object-oriented programming and getters and setters in the public interface, but inside the class you should always directly access the fields.

Without JIT, direct access to the field is about 3 times faster than calling a trivial getter. With JIT (where direct access to a field is cheaper than access to a local one), direct access to a field is about 7 times faster than calling a trivial getter.

Please note: if you use ProGuard, you can use worlds because ProGuard can use additional tools for you.

+2
source

If the method is a simple getter without processing, this is not a problem. If this is due to extensive calculation, the property will not do what you want anyway.

The only time I will worry about any difference is a hard loop with a huge number of iterations (many thousands). Even then this is probably only a problem, if you use aspects to drag and drop additional processing (for example, logging), this can include the creation of thousands of additional objects (for example, combining points and auto-boxing parameters) and problems with the GC.

0
source

I would not worry about the difference in performance. You better not think about it and instead spend time profiling your code in a realistic scenario. You will most likely find that the slow parts of your program are not where you think.

0
source

This post talks about the CLI virtual machine instead of the JVM, but each of them is capable of doing such things, so I think this is relevant.

I solve this specific problem in a special way for my JIT. Note that the description here is conceptual, and the code implements it somewhat differently for performance reasons. When I load the assembly, I make a note in the method descriptor if it simply returns a member field. When I use other methods again, I replace all call instructions with these methods in byte code with the ldfld instruction before passing it to the native code generator. That way I can:

  • Save time in JIT ( ldfld reduces CPU time to JIT than call ).
  • Built-in properties even in the base compiler .
  • By and large, ensuring that using the public properties / private fields template does not result in a performance penalty of any kind when the debugger is disconnected. (When a debugger is connected, I cannot embed accessors.)

I have no doubt that big names in VM technologies already implement something similar (and probably better) in their products.

0
source

All Articles