Java中的受保护类结构是什么?

6

我想知道在Java中是否有一种语言特性,使得超类的方法对于子类的成员不可见:

 public class Subclass extends protected Superclass

或者其他。我给你举个例子。

这是你的超类。

public class A{
    public String getA(){...}
    public String getB(){...}
    public String getC(){...}
    public void setA(String a){...}
    public void setB(String b){...}
    public void setC(String c){...}
}

如果你想要继承A类,但又想保护其中的一些方法,而且除非你覆盖它们,否则你不能更改这些方法中的访问修饰符,那么你最终会得到类似于以下代码的结果-
public class B extends A{
    private String getA(){return super.getA();}
    private String getB(){return super.getB();}//These four methods have
    private void setA(String a){super.setA(a);}//to be redeclared.
    private void setB(String b){super.setB(b);}

    public String getC(){return super.getC();}//These two methods can be
    public void setC(String c){super.setC(c);}//removed.
    public String getD(){...}
    public void setD(String d){...}
}

要么你可以保留 A 的私有实例,并使用如下代码:

或者您可以保留 A 的私有实例,并使用以下代码:

public class B{

    private A obj;

    private String getA(){return obj.getA();}
    private String getB(){return obj.getB();}//These four methods can also
    private void setA(String a){obj.setA(a);}//be removed.
    private void setB(String b){obj.setB(b);}

    public String getC(){return obj.getC();}//These two methods are
    public void setC(String c){obj.setC(c);}//redeclared.
    public String getD(){...}
    public void setD(String d){...}
}

你是否可以有一种方法,既能够接受两种方式,又不必重新声明任何方法?

3个回答

10

在Java中,不存在“非公共”继承,这与C ++的情况不同。

继承创建了一个子类型关系。B的任何实例也是A的实例,并且应该响应相同的消息。如果B的实例明显无法响应A的所有消息,则无论如何都不适合使用继承。

您的最后解决方案(B不继承自A)是适当的:您不会创建一个子类型关系,只需使用一个类型来(秘密地)实现另一个类型即可。


+1 用于与C++进行比较(C++具有保护和私有继承)。 - C. K. Young
当我曾经教授高级C++时,我曾经画维恩图来展示子类型关系,并展示子类内外部分别看到的内容,发现这是非常有效的演示概念的方法。然而,我感觉这样做往往比它所值得的麻烦多了。 - Uri

3

我不认为这是可能的,也不应该是。

如果您使用继承以使B扩展A,则应该能够将B对象用作A对象。例如,可以这样实现:

A obj = new B();

现在程序无法知道您不能调用A的某些公共方法。 没有继承,函数的重新定义是不可避免的。

2

除了将超类中的字段/方法设置为私有,我认为没有其他方法可以解决这个问题。

我认为你最好的选择是第二个选项,其中B类持有对A类的私有引用。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接