在不知道它的情况下保留Java中参数的子类型(或如何找到它?)

时间:2014-11-02 02:40:13

标签: java parameters subclassing

我的Java生疏如此,这完全让我感动。我确定答案很简单,但这是一个简单的示例方法,可以关闭一个Thingy(如果已经打开了一个),另一个关闭:

private Thingy store;
public void switchiton(final Thingy pThingy) {
    if (store != null)
        store.endit();
    pThingy.startit();
    store = pThingy;
}

问题:pThingy可能是子类(例如CleverThingy),而不是超类(Thingy),而CleverThingy会覆盖endit方法。< / p>

该代码将始终在endit中运行Thingy方法 - 而不是CleverThingy中被覆盖的方法(因为它被声明为Thingy而不是一个CleverThingy)。

显然,该方法不知道(也不应该需要)关于子类。

我错过了什么,正盯着我的脸?

更新

在这种情况下创建的子类&#34;在运行中&#34; (不确定正确的术语)而不是正式延长 - 例如在我的Game课程中我有:

startthingy = new Thingy();
gamethingy = new Thingy() {
    @Override
    public void endit() {
        // override things in here
        super.endit();
    }
}

switchiton(gamethingy);  // DOES call gamethingy's overridden startit
switchiton(startthingy); // << gamethingy's overridden endit is NOT called!?

2 个答案:

答案 0 :(得分:0)

关闭此功能的最简单方法是自己回答,我认为......

评论者证实我认为它应该如何工作实际上应该如何 - 这意味着错误显然在代码的其他地方......

我将重新编写所有匿名类,以便更容易调试并更改其中一些更可疑的行为,以期跟踪错误

我问过的核心问题 - 这不是一个问题,所以......

谢谢!

答案 1 :(得分:-1)

我不知道这是否正是您正在寻找的答案(因为它改变了Thingy类而不是switchItOn()方法),但我认为我找到了一个相当简单和安全的解决方案来解决您的问题。如果你担心有人会扩展Thingy并且没有正确地执行endit()方法需要做的任何事情,那么你可以让它成为最终的。这样就可以在endit()方法中完成任何操作,并且不能覆盖该方法。

如果您仍希望子类能够具有该类的灵活性,您可以尝试这样的事情:

public class Thingy {

    public void storeIt() {
        //do stuff
    }

    public final void callEndIt() {
        //do whatever stuff needs to be done every time in order for your program to work
        endIt();
    }

    public void endIt() {
        //this can be extended by subclasses safely
    }

}

然后,您可以随时调用callEndIt()而不是endIt(),这样您就可以完成所需的任何安全预防措施。