Reputation: 111
String a = null;
String b = null;
try {
a.equals(b.toString());
} catch (Exception e) {
e.printStackTrace();
}
I know that a NPE will be thrown, but what I want to know is will it be thrown by b.toString()
before a.equals()
is called?
Upvotes: 1
Views: 96
Reputation: 3019
As the others have pointed out, the error will come from b.toString()
.
You can see this, by changing things around a little bit:
public class Foo {
public static void main(final String[] args) {
Foo a = null;
Foo b = new Foo(); // Won't throw a NPE now.
try {
a.equals(b.foo());
} catch (final Exception e) {
e.printStackTrace();
}
}
public Foo foo() {
throw new AssertionError("Some other error");
}
}
Which will throw the error:
Exception in thread "main" java.lang.AssertionError: Some other error
at Foo.foo(Foo.java:19)
at Foo.main(Foo.java:12)
Verifying that the error will come from the parameters.
Viewing the Bytecode will also show the order of execution. The bytecode for the try
block:
TryCatch: L6 to L7 handled by L8: java/lang/Exception
L3 {
aconst_null
astore1
}
L5 {
new float
dup
invokespecial Foo <init>(()V);
astore2
}
L6 {
aload1
aload2
invokevirtual Foo foo(()LFoo;);
invokevirtual java/lang/Object equals((Ljava/lang/Object;)Z);
pop
}
L7 {
goto L2
}
L8 {
astore3
}
L1 {
aload3
invokevirtual java/lang/Exception printStackTrace(()V);
}
L2 {
return
}
L4 {
}
In L6, the Foo#foo()
method is called on the line before Object#equals(Object)
is called. So the error will be thrown from b
in both cases.
Upvotes: 1
Reputation: 11173
Yes the exception will be thrown from B.toString()
. Since A.equals()
method will come to the scene after B.toString()
evaluated.
Upvotes: 0
Reputation: 7804
It will be thrown for B.toString()
. Stack of expression is created and stack is a LIFO data structure. B.toString()
goes in last and come out first.
Upvotes: 0
Reputation: 280167
Yes, arguments in method invocation expressions are evaluated before the method invocation itself. So the exception will be raised for B.toString()
.
Upvotes: 1