Assuming I have defined a string like this:
priv开发者_如何学Pythonate final static String s = "To Be or not to be, that is the question";
And in one of the (static) methods I call a method that receives a String as a parameter:
methodThatReceivesString(s.charAt(0) + s.charAt(1) + "Inter" + s.charAt(3) + s.charAt(4))
(the idea is that methodThatReceivesString()
will be passed the value "ToInterBe")
My question is: Will the Java compiler optimize the code such that the compiled binary file (.jar .dex) already contain "ToInterBe"?
Or will this occur only at the application's run time?
The Java compiler won't do this as it would technically change the program, since the methods involved could have side effects at runtime. But even if it would precompute the string it would still need to put the original string into the class file since it could be accessed by refection, could be relevant for a annotation or for other reasons.
I think the tool you are looking for is ProGuard. This can among many other things actually remove the string if no code refers to it anymore after all statically decidable code was precomputed.
A Java compiler is not permitted to optimize this.
The issue is that method calls on constant objects are not defined to be constant expressions; see JLS section 15.28 for a list of the things that you can do in a constant expression. Thus, s.charAt(0)
is not a constant expression even though s
is a constant expression, and "we know" that its value will always be 'T'
. Since it is not a constant expression, it has to be evaluated at runtime.
If your aim in doing this is to prevent the string "ToInterBe"
from appearing in the classes constant pool, then you've succeeded. But that's not going to slow down a good reverse engineer by more than a couple of minutes.
(By the way, that expression probably doesn't do what you expect. The first +
subexpression is an addition (not a string concatenation) because neither of the operands is a String. The result of that addition will be an int
, so the entire expression will evaluate to "195InterBe"
... I think.)
精彩评论