在Java中,在创建类和接口以及处理继承时,是否有明确的规则来确定何时使用每个访问修饰符,即默认的(包私有)、公共的、受保护的和私有的?


当前回答

简单的规则。首先声明所有内容都是私有的。然后,随着需求的出现和设计的需要,向公众迈进。

当公开成员时,问问自己是公开表示选择还是抽象选择。第一种是您需要避免的,因为它会引入太多对实际表示的依赖,而不是对其可观察行为的依赖。

作为一般规则,我试图通过子类化来避免重写方法实现;搞砸逻辑太容易了。如果要重写抽象受保护的方法,请声明该方法。

此外,在重写时使用@Override注释,以防止重构时出错。

其他回答

简而言之

公共:随处可见。protected:可由同一包的类和驻留在任何包中的子类访问。默认(未指定修饰符):可由同一包的类访问。private:只能在同一类中访问。

当谈到访问修饰符时,我们很容易理解,非常简单的规则包括它们。

专用访问修饰符用于:-仅同一类

默认Access修饰符用于:-仅同一类/同一包子类

Protected Access修饰符用于:-同一类/同一包子类/同包非子类/不同包子类

公共访问修饰符用于:-我们可以在任何地方使用(相同的类/相同的包子类/相同包非子类/不同的包子类别/不同包非子类别)

这是该表的一个更好的版本,其中还包括一个模块列。


解释

私有成员(i)只能在声明的同一类中访问。没有访问修饰符(j)的成员只能在同一包中的类中访问。受保护的成员(k)可以在同一包中的所有类和其他包中的子类中访问。公共成员(l)对所有类都是可访问的(除非它驻留在不导出声明它的包的模块中)。


要选择哪个修饰符?

访问修饰符是一种帮助您防止意外破坏封装(*)的工具。问问自己,您是否希望成员是类、包、类层次结构的内部成员,或者根本不是内部成员,并相应地选择访问级别。

示例:

长字段internalCounter可能应该是私有的,因为它是可变的,并且是实现细节。只应在工厂类中实例化的类(在同一个包中)应具有包限制构造函数,因为不可能从包外部直接调用它。应保护在呈现之前调用并用作子类中钩子的内部void beforeRender()方法。从GUI代码调用的void saveGame(File dst)方法应该是公共的。

(*)封装到底是什么?

我经常意识到,通过创造真实世界的类比,记住任何语言的基本概念都是可能的。下面是我在Java中理解访问修饰符的类比:

让我们假设你是一个大学的学生,你有一个朋友周末来拜访你。假设校园中央有一座大学创始人的大雕像。

当你把他带到校园时,你和你的朋友首先看到的就是这尊雕像。这意味着任何在校园里行走的人都可以在没有大学许可的情况下观看雕像。这使雕像成为公共的。接下来,你想带你的朋友去你的宿舍,但为此你需要将他登记为访客。这意味着他可以获得进入校园各个建筑的通行证(与你的通行证相同)。这将使他的门禁卡受到保护。你的朋友想登录校园WiFi,但没有任何凭据。他唯一可以上网的方式是你和他分享你的登录信息。(记住,每个上大学的学生都拥有这些登录凭据)。这将使您的登录凭据为NO MODIFIER。最后,你的朋友想看看你在网站上发布的学期进度报告。然而,每个学生都有自己的个人登录来访问校园网站的这一部分。这将使这些凭据成为PRIVATE。

希望这有帮助!

官方教程可能对您有所帮助。


Class Package Subclass
(same pkg)
Subclass
(diff pkg)
World
public + + + + +
protected + + + +
no modifier + + +
private +

+:可访问空白:不可访问