我永远不能直接实例化控制台,因为它是抽象的
你是对的,但是...假设Console 被定义为
public abstract class Console implements Gaming {
// no impl. not needed because already declared in Gaming
// just for clarity
public abstract void play();
}
你可以直接实例化Console:
Console myAnonymousConsole = new Console() {
public void play() { System.out.println("Hello there"); }
};
不过,我可以将控制台实例化为 xbox
再次正确,因为 Xbox 不是 abstract。
控制台收藏 = new Xbox();
如果所有类都定义了 play() 方法。如果我打电话给 fav.play();它将查看 Xbox 的播放方法,如果它没有播放方法,它会继续向上层级,直到找到该方法?
从某种意义上说是的。
如果我做了 ((XboxOne)fav).play() ,它会做 XboxOne 的播放方法吗?我也只能投射层次结构中较低的对象吗?
您不能相对于实际的实例类型向下转换。你可以写(但味道不好)。
Console a = new XBoxOne();
XBox b = (XBox)a; // ok because a is-a Xbox
XBoxOne c = (XBoxOne)a; // ok because a is-a XBoxOne
Console a = new XBox();
XBox b = (XBox)a; // ok because a is-a Xbox
XBoxOne c = (XBoxOne)a; // ko! because a is-not-a XBoxOne
检查在运行时完成。在第二个示例中抛出了ClassCastException。
如果 Xbox 类有 getGamerscore 方法但控制台没有,我可以运行 fav.getGamerScore() 吗?
如果fav 被声明为控制台,则否。不过你可以在Console 中声明getGameScore()。
一般问题:
= 左侧的类型显示了调用方法时 java 将查看哪个类(最具体的)? (如果它在那里找不到它,它将继续沿着层次结构向上直到找到方法?)
不是真的。您必须从上到下考虑继承:当一个类extends 另一个时,它继承所有public(和protected)方法/字段.例如,如果XBoxOne 没有定义play() 方法,它_从XBox 继承它。
回到您的问题,就在左侧类型中声明的方法(此处为Console)而言,调用的正确方法实现将由实例的实际运行类型确定 - 这是 多态性 em>。
public class XBox extends Console {
public void play() { System.out.println("In XBox");
}
public class PS3 extends Console {
public void play() { System.out.println("In PS3");
}
List<Console> consoles = Arrays.asList(new XBoxOne(), new PS3());
for (Console c : consoles) {
c.play(); // polymorphism here
}
打印
In XBox
In PS3
即使List 看到只有Console 类型。另请注意,XBoxOne 的实例化类型继承来自XBox 的play() 方法。
右边的类型只代表编译类型。编译java时会查看方法或数据是否属于编译类型,如果是,一切都很好? Java 在运行时将不再查看它的编译类型。
不,见上文。
强制转换只是帮助解决编译问题?
是的,而且大部分时间都可以避免。
如果我想使用某个方法,但我的对象编译类型就像一个接口或抽象类或其他东西,所以我进行了转换,以便在我尝试访问运行时类型的方法时编译器不会抱怨?
我觉得你这里左右混了,看上面的cmets