wood burning stoves 2.0*
The moose likes Performance and the fly likes Calls trough interface references are slower (on Android) Big Moose Saloon
  Search | Java FAQ | Recent Topics | Flagged Topics | Hot Topics | Zero Replies
Register / Login


Win a copy of Murach's Java Servlets and JSP this week in the Servlets forum!
JavaRanch » Java Forums » Java » Performance
Bookmark "Calls trough interface references are slower (on Android)" Watch "Calls trough interface references are slower (on Android)" New topic
Author

Calls trough interface references are slower (on Android)

Cristian Vrabie
Ranch Hand

Joined: Jul 09, 2008
Posts: 71
In the 2009 Google I/O talk about writing real-time games for Android http://developer.android.com/videos/index.html#v=U4Bk5rmIpic it is recommended that for performance we don't use interfaces. Supposedly the calls through an interface reference are about 30% slower. It is also mentioned that calls to static methods are faster.

In these circumstances, i asked myself if all calls to a non-direct reference are slower. I'm not an expert at low level stuff, but it looks to me that calling a method through a interface reference is about the same thing as calling a method through a reference to a parent class. But this would mean that we shouldn't use inheritance at all. And that, for someone like me that usually trades performance for scalability, it sounds crazy.

I decided to make a quick test to see if this is true. Here's the code I used: http://pastebin.com/m7c7c0043

First I ran it on my PC and I was stupefied to find results like these at every run:
Direct refference => 1,596,318,257
Parent refference => 1,550,725,582
Interface refference => 1,552,626,591
Static refference => 1,751,394,872

So the interface calls are about the same. Actually sometimes they were faster by a negligible amount.

Then I tested it in an Android application, using a HTC Hero Phone. (Note: I reduced the number of iterations from 1000000000L to 5000000L).
Results were something like:
Direct refference => 3,767,791,749
Parent refference => 3,477,020,264
Interface refference => 4,690,185,547
Static refference => 3,327,636,719


So the interfaces are slower. I can now confirm with my own test. I guess the virtual machine is quite different.
The good thing is that calls through parent references are not slower. Wohoo! OOP for life

What do you guys think? I'm especially interested if the code I used is a good test case.
Also, I'm genuinely interested why interfaces are slower. I guess some king of lookup is done at runtime. But then why doesn't this happen for references to a parent class. In my example, the child class overrides the parent class so the same lookup should occur to tell the jvm to run the method in the child not the one in the parent.
Andrei Matyas
Greenhorn

Joined: Apr 15, 2007
Posts: 25
Just curios ...could you re-do your test calling a final method (your implemented method is final ...or ..your implementig class is final). Basically I want to know if inlined methods changes something in your case.

10x
Cristian Vrabie
Ranch Hand

Joined: Jul 09, 2008
Posts: 71
Ya. I was thinking to do that myself. Here is the re-run:

On PC (sun-jdk):
Direct refference => 1,546,818,889
Direct refference (final method) => 1,544,656,939
Parent refference => 1,548,618,054
Interface refference => 1,552,144,756
Static refference => 1,737,086,755


On Android (1.5):
Direct refference => 3,650,238,037
Direct refference (final method) => 3,492,218,018
Parent refference => 3,484,863,281
Interface refference =3,869,232,177
Static refference => 3,345,306,297


I ran the test several times. I couldn't notice any real difference for final methods, though in theory there should be as final methods are not virtual.
Anyone around that can explain. Pretty please?!
Cristian Vrabie
Ranch Hand

Joined: Jul 09, 2008
Posts: 71
Btw. I keep noticing that there is a small difference for static methods on PC. That makes it even more weird. Static methods should be faster right? The calls to static methods are resolved at compile time so no polymorphism lookup should occur.
Andrei Matyas
Greenhorn

Joined: Apr 15, 2007
Posts: 25
This is quite strange. Static calls should be faster. What java version do you use. I've tested it on java 5&6 (on vista) and indeed static calls are faster.


Cristian Vrabie
Ranch Hand

Joined: Jul 09, 2008
Posts: 71
Sun JDK on Linux Ubuntu 9.10.
java version "1.6.0_15"
Java(TM) SE Runtime Environment (build 1.6.0_15-b03)
Java HotSpot(TM) Server VM (build 14.1-b02, mixed mode)

The difference is pretty small though. It might be e "fluke" or an inaccuracy of my testing code.
Martin Humby
Greenhorn

Joined: Mar 31, 2011
Posts: 3

Copied the test app. into Eclipse and ran it: Java 1.6.0_24, Windows XP Pro. Pentium E5200 at 3.1GHz. Bad move - weird results:

Slightly reduced performance could be accounted for by factors like running under Windows, network intrusions, age of this machine, but extended parent-reference speed does not compute. Now have compelling need to find out what is going on. To get a bit of a baseline converted app. to C++, code at http://pastebin.com/X8YzUS4a, compiled to native code.

Whee! Java is faster than C++ - mostly .

Still not happy, what happens if method modifies a field? Java: http://pastebin.com/jzjtScHq, C++: http://pastebin.com/SJwHc3YG. This arrangement gives a chance to compare calls with updating a field directly. Results in table: parent reference anomaly still there but nice to see that direct field-access gets little or no advantage. What Java needs now is properties to neaten up setter and getter code, preferably based on the original Delphi syntax with the single line option rather than the C# version .

Otherwise guess the next move is buy a JVM / Byte-code book. Can anyone recommend one?
 
wood burning stoves
 
subject: Calls trough interface references are slower (on Android)
 
Similar Threads
method call from super/sub object ref.
Data Hiding
inheritance instantiation order and lost variables
Overriding/overloading
JDBC Interfaces