在查看此处显示的var功能之后:
我在使用JDK 10设置Eclipse/IntelliJ IDEA IDE时遇到了困难,因此请求具有可用Java 10环境的Stack Overflow用户提供帮助.
考虑以下:
public class A {
public void someMethod() { ... }
}
public class B extends A{
@Override
public void someMethod() { ... }
}
...
...
...
var myA = new A(); // Works as expected
myA = new B(); // Expected to fail in compilation due to var being
// syntactic sugar for declaring an A type
myA = (A) (new B()); // Should work
myA.someMethod(); // The question - which someMethod implementation is called?
Run Code Online (Sandbox Code Playgroud)
在使用时var,我希望JVM能够识别变量所包含的派生类类型.并且在执行myA.someMethod()时执行B:someMethod()而不是A:someMethod().
确实如此吗?
感谢nullpointer提供了一个在线Java 10编译器的链接,我得到了以下有趣的结果:
public class Main {
static class A {
public void someMethod() { System.out.println(this.getClass().getName()); }
}
static class B extends A{
@Override
public void someMethod() { System.out.println("Derived: " + this.getClass().getName()); }
}
public static void main(String[] args) {
var myA = new A();
myA.someMethod();
myA = new B(); // does not fail to compile!
myA.someMethod();
}
}
Run Code Online (Sandbox Code Playgroud)
产出:
Main$A // As expected
Derived: Main$B // As expected in inheritance
Run Code Online (Sandbox Code Playgroud)
结论 - var是句法糖:
var myA = new A()等同于A myA = new A()所有与之相关的OOP.
PS:我尝试使用一个包含匿名类的var来玩一点并提出这个有趣的行为 - 再次感谢nullpointer,因为我们不能将两个推断变量分配为匿名类彼此:
static interface Inter {
public void method();
}
public static void main(String[] args) {
var inter = new Inter() {
@Override
public void method() {System.out.println("popo");}
};
inter.method();
inter = new Inter() {
@Override
public void method() {System.out.println("koko");}
};
inter.method();
}
Run Code Online (Sandbox Code Playgroud)
并输出:
Main.java:11: error: incompatible types: <anonymous Inter> cannot be converted to <anonymous Inter>
inter = new Inter() {
^
Run Code Online (Sandbox Code Playgroud)
由于第二个匿名类类型与第一个匿名类类型不同,因此对var的第二个赋值失败 - 强制执行var关键字的语法糖角色.
令人惊讶的是,错误消息不再精确 - 目前它没有多大意义,因为错误中显示的类型名称是相同的!