【问题标题】:Controlling Class Visibility in Java在 Java 中控制类的可见性
【发布时间】:2017-03-30 13:26:39
【问题描述】:

我的项目目前具有以下包结构。

这里我添加了一个包名utils,并在其中定义了与该模块相关的所有实用程序类。这些已被其他包(即implinternal)使用,因此我在utilpublic 中创建了类和方法。

因为它是公共的,不仅此模块中的类,其他模块中的类也可以访问它,当我使用我的 IDE 编码时,它们会显示为编码建议。

我浏览了几篇研究论文,这些论文描述了这会如何降低 API 的可用性并给参与开发的开发人员带来糟糕的体验 [ref1ref2]

我了解 java 不允许我使 util 中的类可以访问 impl 和内部包,而不是其他人。

将我的实用程序类放到包“util”中是否正确?还是应该将所有相互通信的类放到同一个包中?

【问题讨论】:

  • 就 OOP 设计而言,您不应该有实用程序类 :)
  • 我用了不好的例子吗? o.O
  • 您使用的是哪个 IDE?在 Eclipse 中,作为代码建议显示的第一个类是同一包中或导入的类中的类(包括java.lang.*)。确实会出现其他公共类,但它们会显示在这些类之后。
  • 我正在使用想法。由于这些类根本不打算在其他包中使用,所以我试图让其他包无法访问它们。由于我使用 OSGI 来加载我的模块,如果不小心有人会在 IDE 建议的不同类中使用它,则会导致运行时错误。
  • 这可能有点矫枉过正,但随着应用程序的增长,管理多个项目的代码库会更容易。例如,应用程序的每个功能层都在自己的项目中。这可以在其自己的项目中包含 util 类,其中 util.jar 只是成为需要它的其他项目的依赖项。这有助于避免 util 类成为垃圾抽屉,因为开发人员必须有意去另一个项目添加新的 util 类/方法。根据构建工具的不同,这也将强制 util 类是通用的,以避免循环依赖。

标签: java api usability access-modifiers


【解决方案1】:

你是对的,标记为 public 的东西可以在 任何 其他包中使用。与其他语言相比,Java 不提供除此之外的任何控制。

一个简单的解决方法:拥有 一个 包含那些 public 内容的特殊包可能会有所帮助,这些内容应该可供您的外部用户使用。

含义:创建类似com.whatever.product.api 的内容 - 并告知您的用户他们可以使用那里的所有内容 - 但仅此而已。

换句话说:您将所有需要public的东西public;但是你把这些东西收集在一个你允许别人使用的特殊地方。

值得一提的是,Java9 将引入 modules 的概念,它允许您定义哪些包应该对用户公开 您的模块。从这个意义上说,java 9 模块允许您区分“内部”和“外部”public

【讨论】:

    【解决方案2】:

    Util 类很好。实用程序类是在项目中的多个位置使用但并不真正属于特定类的功能。

    在一个完美的 OOP 世界中不会有任何 util 类,但是如果它们不属于特定类,则创建 util 类被认为是一种好习惯。

    此处列出了您的访问修饰符选项: https://docs.oracle.com/javase/tutorial/java/javaOO/accesscontrol.html

    有一种方法可以实现您想要的,但它被认为是一种非常糟糕的做法。您可以将 util 类的访问修饰符更改为 protected。这将使您的 util 类可以从子类和包中访问。因此,如果一个类需要访问其中一个 util 类,那么它必须扩展这个 util 类,从而成为一个子类。 我怎么强调都不为过,这是一种非常糟糕的做法。

    【讨论】:

    • 那么我可以假设我使用的包结构是通用的并且没有任何问题吗?
    • 您的帖子没有包含足够的详细信息来确定您的项目结构,除了包名称。将项目分成多个包是一种很好的做法。你提到过一些关于 API 的事情吗?您是否正在尝试创建 API?
    • 请记住,如果有人想使用您的 utils 类,那么他们必须导入该包,否则他们将看不到它。因此,只要它们不导入您的实用程序类,它就会自行处理。
    • github.com/wso2-extensions/identity-workflow-impl-bps/tree/…这是项目的一部分,我们可以把这个jar放到m2中,在其他代码中访问。org.wso2.carbon.identity.workflow.impl包中的类是API .不同的项目可以通过它们访问功能。其他包中的其他类(例如:dao)不应该被外部类访问。
    • 我快速浏览了一下。看起来您的实用程序类是“真正的”实用程序类,它们似乎与其余代码无关。祝你的项目好运!
    猜你喜欢
    • 2011-01-24
    • 2011-04-19
    • 2012-07-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-11-20
    • 2013-02-25
    • 2011-12-20
    相关资源
    最近更新 更多