包访问权限是Java模块级封装的关键手段,它通过默认修饰符实现同包内自由调用、跨包不可见的天然边界,既保障内聚协作又杜绝越界依赖。

Java 中封装不只是靠 private,包访问权限(即默认修饰符)是实现模块级封装的关键手段。它让“同一个业务模块的代码”自然聚合成一个协作单元,既不暴露给外部,又保留内部灵活调用的能力。
包访问权限是模块内聚的天然边界
把订单服务相关类(如 OrderValidator、InventoryDeductor、PaymentAdapter)统一放在 com.example.order 包下,它们之间用默认权限声明辅助方法或工具类:
-
AmountParser.parse(String)不加修饰符 → 同包类可直接调用 -
OrderBuilder.state字段设为默认 → 构建逻辑在包内自由流转,但外部无法 new 出半成品对象 -
InternalEventPublisher类本身不加public→ 外部包连 import 都做不到,更别说使用
这种组织方式不需要额外文档说明“仅供内部使用”,语言机制本身就在表达约束。
它比 public + 注释更可靠,比 private + 反射更安全
-
public void doSomething()加注释说“请勿外部调用”,IDE 不拦、编译不报错,别人照样能用 -
private虽然彻底封死,但会让同包的测试类、工厂类、Builder 模式卡住——你总不能为了封装,把单元测试写成反射调用吧 - 默认权限正好落在中间:包内畅通无阻,包外连编译都过不去,既支持合理协作,又杜绝随意依赖
实际开发中它让封装真正落地
立即学习“Java免费学习笔记(深入)”;
- DTO 的构造逻辑、状态校验方法设为默认,API 层只能走
build()入口,不能绕过校验直接 new - 工具类里的解析、转换、格式化方法用默认权限,业务服务可复用,但 Web 层或 RPC 接口层无法直连底层细节
- 模块升级时,只要不改包名,原有调用不受影响;一旦拆包,编译失败立刻暴露越界依赖,而不是等到上线后才报
IllegalAccessError
包不是目录别名,它是代码的行政区划。包访问权限就是它的边界哨卡——不靠自觉,不靠约定,编译器和 JVM 在语言层面就把它钉死了。


















