是否可以在Java中使用扩展类的getter / setter

时间:2013-04-04 13:35:48

标签: java

我有以下

public abstract class MyData
{
      private String sID;
      public void setsID(String sID) {
        this.sID= sID;
    }
       public String getsID() {
        return sID;
    }
} 

此基类正由另外两个类扩展

public class DataTypeOne extends MyData
{
       private String sName;
       public void setsName(String sName) {
        this.sName= sName;
        }
           public String getsName() {
            return sName;
        }
}


public class DataTypeTwo extends MyData
{
       private String sSummary;
       public void setsSummary(String sSummary) {
        this.sSummary= sSummary;
        }
           public String getsSummary() {
            return sSummary;
        }
}

我正在按如下方式初始化这个类

MyData oDataOne = new DataTypeOne();
MyData oDataTwo = new DataTypeTwo();

原因是我有一个工厂方法,它会给我一个基于类型(一或两个)的类

使用oDataOne& oDataTwo,我可以从基类访问getsID()但不能访问getter&各个班级的制定者。

我如何访问这些?我

4 个答案:

答案 0 :(得分:3)

您无法访问不存在的方法。你曾经承诺过你的Java编译器oDataOneoDataTwoMyData个对象。由于MyData类没有特定于实现的方法,因此您不能要求Java调用这些方法(因为它认为它们不存在)。

如果要访问这些方法,则需要将对象转换为实际具有正确方法的类,或者可以将抽象方法存根添加到基类,这将告诉Java这些方法实际存在。

类型转换在短期内更容易编写,但不太清楚,您可能会遇到更多麻烦:

((DataTypeOne) oDataOne).getsName();
((DataTypeTwo) oDataOne).getsSummary(); // Throws ClassCastException!

添加抽象存根更加健壮,但如果不是所有具体的子类都应该实现所有抽象方法,则可能没有意义:

public abstract class MyData {
    public abstract void setsName(String name);
    public abstract String getsName();
    public abstract void setsSummary(String summary);
    public abstract String getsSummary();
}
public class DataTypeOne extends MyData {
    public String getsName() {
        // implement
    }
    public void setsName(String name) {
        // implement
    }

    // Still have to implement these!!!
    public String getsSummary() {
        // raise an exception or something if appropriate
    }
    public void setsSummary(String summary) {
        // raise an exception or something if appropriate
    }
}
// Same for DataTypeTwo

答案 1 :(得分:1)

由于您将变量声明为MyData,因此您只能访问MyData的方法。您可以通过将子类方法强制转换为DataTypeOne或DataTypeTwo来获取子类方法:

 ((DataTypeOne)oDataOne).getsName()

但是您需要确保它是DataTypeOne类型,否则您将获得ClassCastException

答案 2 :(得分:0)

MyData类型的对象不知道是否有任何其他类扩展它,因此无法访问这些类的成员。

您必须将对象转换为特定类型才能访问特定成员。

如果您发现自己处于这种情况,您可以非常确定您的设计存在缺陷。如果您需要为每种类型的MyData扩展程序执行特定操作,请在界面中添加一个方法,例如specialAction(),并隐藏其中的详细信息。这消除了找出你正在处理哪个子类的全部需要。

答案 3 :(得分:0)

MyData oDataOne = new DataTypeOne();

这表示,您的oDataOne对象属于MyData类型。即使它被创建为DataTypeOne,java也只能确定它是一个MyData实例。

如果您确定MyData实例实际上也是DataTypeOne实例,则可以投射然后访问DataTypeOne方法+ MyData方法。< / p>

确保对象属于特定类型测试:

if(oDataOne instanceOf DataTypeOne){
    ((DataTypeOne) oDataOne).getsName();  // this will return the Name if oDataOne is really of the type DataTypeOne
}