Code style vs efficiency
I think that programing in Java, like a hight level language it better keep a clear an explicit code like
int b=0;
if (a){
b=1;
} else {
b=0;
}
but, in the other hand, we can write all of this in a single line like
int b= (a) ? 1 : 0;
but, once both codes being compilated and becomes bytecodes... are equals? or generate best bytecodes the second one?
Thanks!
[429 byte] By [
Alcaudona] at [2007-10-3 4:18:36]

This level of optimization is of academic interest only. Most of the time in a program is usually spent doing I/O.Most bottle necks are due to incorrect algorithms, not coding style.It's best practice to write clear code and save optimization until you have observed a problem and run some profiling.
And FWIW, in your example above, the use of the ternary operator is much cleaner and easier to understand.
Thaks pkwooster. I agree with you that, and that I learn in the university, but my questions is if javac or another compiler generates the same machine-code or bytecodes.
I suspect that the compiler must generate the same bytecodes, althougth the two samples not equal, at last they must do the same operations.
but how can i verify it?
void longWay(boolean a) {
int b=0;
if (a) {
b=1;
} else {
b=0;
}
}
void longWay(boolean);
Code:
Stack=1, Locals=3, Args_size=2
0:iconst_0
1:istore_2
2:iload_1
3:ifeq11
6:iconst_1
7:istore_2
8:goto13
11:iconst_0
12:istore_2
13:return
//:~
void shortWay(boolean a) {
int b = (a) ? 1 : 0;
}
void shortWay(boolean);
Code:
Stack=1, Locals=3, Args_size=2
0:iload_1
1:ifeq8
4:iconst_1
5:goto9
8:iconst_0
9:istore_2
10:return
//:~
void longWayShortened(boolean a) {
int b=0;
if (a) b=1;
}
void longWayShortened(boolean);
Code:
Stack=1, Locals=3, Args_size=2
0:iconst_0
1:istore_2
2:iload_1
3:ifeq8
6:iconst_1
7:istore_2
8:return
// NOTE: shortWay will execute the fewest instructions
The first will be slightly slower, unless the compiler is very clever, since it's more general and it assigns variable b twice, once when initialized and once in the conditional.It will also take slightly longer to compile. The readablity of the second choice is better when the expressions are short, but it tends to get unreadable if they get long. The first choice is better for debugging since it allows more places to set breakpoints.
I use them both depending on the circumstances.
void longWayShortened(boolean a) {
int b=0;
if (a) b=1;
}
I probably use this more frequently than the other 2 put together.
by usign "javap -c" on the following code,
public class test {
public static int style1(boolean a) {
int b=0;
if (a){
b=1;
} else {
b=0;
}
return b;
}
public static int style2(boolean a) {
int b= (a) ? 1 : 0;
return b;
}
public static void main(String[] args) {
style1(true);
style2(true);
}
}
I got the following output
public class test extends java.lang.Object{
public test();
Code:
0:aload_0
1:invokespecial#1; //Method java/lang/Object."<init>":()V
4:return
public static int style1(boolean);
Code:
0:iconst_0
1:istore_1
2:iload_0
3:ifeq11
6:iconst_1
7:istore_1
8:goto13
11: iconst_0
12: istore_1
13: iload_1
14: ireturn
public static int style2(boolean);
Code:
0:iload_0
1:ifeq8
4:iconst_1
5:goto9
8:iconst_0
9:istore_1
10: iload_1
11: ireturn
public static void main(java.lang.String[]);
Code:
0:iconst_1
1:invokestatic#2; //Method style1:(Z)I
4:pop
5:iconst_1
6:invokestatic#3; //Method style2:(Z)I
9:pop
10: return
}
Style 2 has less lines of code, so it sould be faster... i think...
It seems that the clear way is less efficient than the shot way, but the best is the smart way :-P.Thanks all.
The HotSpot compiler is clever enough to optimize both versions to be equally fast. Test program below; as always when you are concerned about performance run the program with "java -server".
public class t
{
public static void main(String args[])
{
System.out.println("Ignore the first few timings.");
System.out.println("They may include Hotspot compilation time.");
System.out.println("I hope you are running me with \"java -server\"!");
for (int n = 0; n < 5; n++) {
doit1();
doit2();
}
}
static final int ROUNDS = 100000000;
public static void doit1()
{
int total = 0;
long start = System.currentTimeMillis();
for (int n = 0; n < ROUNDS; n++) {
int b = 0;
if (n % 2 == 0)
b = 1;
else
b = 0;
total += b;
}
long end = System.currentTimeMillis();
System.out.println("time " + (end - start) + " ms, total " + total);
}
public static void doit2()
{
int total = 0;
long start = System.currentTimeMillis();
for (int n = 0; n < ROUNDS; n++) {
int b = n % 2 == 0 ? 1 : 0;
total += b;
}
long end = System.currentTimeMillis();
System.out.println("time " + (end - start) + " ms, total " + total);
}
}
> It seems that the clear way is less efficient than> the shot way, but the best is the smart way :-P.> > Thanks all.I find the second one, with the ? :, easier to read.
jverda at 2007-7-14 22:20:20 >
