杰瑞科技汇

Effective第二版,Java编程核心要点何在?

这本书是 Java 开发领域公认的“圣经”级著作,即使是对于经验丰富的 Java 程序员,也常常作为案头必备的参考手册,它不是一本教你 Java 语法基础的书,而是一本专注于提升代码质量、健壮性、可维护性和性能的最佳实践指南。

Effective第二版,Java编程核心要点何在?-图1
(图片来源网络,侵删)

书籍概览

  • 作者:Joshua Bloch,他是 Google 的首席 Java 架构师,也是 JDK(Java Development Kit)库的早期设计者和主要贡献者之一,这意味着书中的建议都源于对 Java 语言和平台核心库的深刻理解。
  • 版本:第二版,这一版针对 Java 5 和 Java 6 的新特性进行了大量更新和补充,例如泛型、枚举、注解、可变参数等,使其内容与当时的现代 Java 开发实践紧密结合。
  • 核心思想:通过一系列独立的、精心组织的条目,向读者传授如何编写更好的 Java 代码,每个条目都聚焦一个具体问题,解释“为什么”应该这样做,并提供“怎么做”的清晰示例。

与章节结构

第二版全书包含 78 个条目,系统地覆盖了 Java 编程的方方面面,这些条目通常被组织成以下几个主要部分:

第一部分:创建和销毁对象

这是全书的基础,因为对象是 Java 程序的核心,这部分内容强调了构造函数、工厂方法和对象生命周期管理的重要性。

  • 条目 1:考虑用静态工厂方法代替构造函数:介绍如何提供更灵活、有名称的创建对象的方式。
  • 条目 2:遇到多个构造参数时考虑使用构建器:解决“构造器模式”(Telescoping Constructor Pattern)带来的代码膨胀问题,推荐更优雅的 Builder 模式。
  • 条目 3:用私有构造函数或者枚举类型强化 Singleton 属性:提供了实现 Singleton 模式的三种可靠方法,并特别推荐使用枚举类型。
  • 条目 4:通过私有构造函数强化不可实例化的能力:介绍如何创建一个只包含静态方法和变量的工具类,防止被错误实例化。
  • 条目 5:避免创建不必要的对象:强调对象重用的重要性,特别是对于不可变对象。
  • 条目 6:消除过期的对象引用:警惕内存泄漏,特别是在集合、监听器等场景下。
  • 条目 7:避免使用终结方法:解释了 finalizer 的不可靠性和性能问题,并建议使用 try-finallyAutoCloseable(Java 7 引入的 try-with-resources)作为替代方案。

第二部分:对于所有对象都通用的方法

这部分关注 Object 类中定义的方法,如 equals, hashCode, toString 等,并指导如何正确地重写它们。

  • 条目 8:覆盖 equals 时请遵守通用约定:详细解释了 equals 方法的自反性、对称性、传递性、一致性和非空性,并给出了实现模板。
  • 条目 9:覆盖 equals 时总要覆盖 hashCode:解释了为什么违反这条约定会导致无法在 HashMapHashSet 等基于哈希的集合中正常工作。
  • 条目 10:始终要覆盖 toString:建议为所有供他人使用的类提供一个清晰的 toString 实现,方便调试和日志记录。
  • 条目 11:谨慎地覆盖 clone:指出 Cloneable 接口的缺陷,并建议优先提供拷贝构造函数或拷贝工厂方法。
  • 条目 12:考虑实现 Comparable 接口:让对象具备自然排序的能力,可以用于 TreeSetTreeMapCollections.sort()

第三部分:类和接口

这部分探讨了如何设计类和接口,使其更强大、更灵活、更易于维护。

Effective第二版,Java编程核心要点何在?-图2
(图片来源网络,侵删)
  • 条目 13:使类和成员的可访问性最小化:介绍了 Java 访问修饰符(public, protected, package-private, private)的原则,推崇“信息隐藏”。
  • 条目 14:在公有类中访问方法优于公有域:建议使用不可变类或提供 getter/setter,而不是将数据域设为 public
  • 条目 15:使可变性最小化:极力推崇不可变类,并列举了其优点(简单、线程安全、可靠等)。
  • 条目 16:复合优先于继承:这是面向对象设计的一条黄金法则,解释了为什么继承会破坏封装性,以及如何通过“组合”来复用代码。
  • 条目 17:要么为继承而设计,并提供文档说明,要么就禁止继承:如果你确实需要设计一个可被继承的类,必须非常小心,并清晰地说明其所有行为和实现细节。
  • 条目 18:接口优于抽象类:相比于抽象类,接口更灵活,可以多重实现。
  • 条目 19:接口只用于定义类型:不要使用接口来存储常量。
  • 条目 20:类层次优于标签类:避免使用带有“类型标签”的类,应该将其拆分为多个子类。
  • 条目 21:用函数对象表示策略:介绍如何使用匿名内部类(在 Java 8 中是 Lambda 表达式)将行为作为参数传递。

第四部分:泛型

这部分是第二版新增和重点强调的内容,因为 Java 5 引入了泛型,这是一个重大的语言特性。

  • 条目 23:不要在新代码中使用原生态类型:解释了原生态类型(Raw Type)带来的安全隐患和编译器警告。
  • 条目 25:优先使用泛型:鼓励编写泛型类和泛型方法,以获得编译时的类型安全检查。
  • 条目 26:确保在循环中使用的本地变量是泛型:避免在 for-each 循环中使用非泛型的本地变量。
  • 条目 27:优先考虑泛型方法:展示如何编写不依赖于类泛型参数的泛型方法。
  • 条目 28:利用有限制通配符来提升 API 的灵活性:这是泛型中最难但也最重要的概念之一,介绍了 ? extends T (PECS, Producer Extends Consumer Super) 原则。
  • 条目 29:优先考虑类型安全的异构容器:展示了如何利用 Class 对象作为键,创建一个类型安全的、可以存储不同类型对象的容器。

第五部分:枚举和注解

  • 条目 30:用 enum 代替 int 常量:介绍了 enum 类型带来的类型安全、可扩展性和健壮性。
  • 条目 31:用实例域代替序数:警告不要使用 enumordinal() 方法来获取序数,而应该为每个实例定义一个独立的域。
  • 条目 32:用 EnumSet 代替位域EnumSet 是专门为枚举集合设计的,性能远优于位域。
  • 条目 33:用 EnumMap 代替序数索引EnumMap 是专门为枚举键设计的 Map 实现,高效且类型安全。
  • 条目 34:用接口模拟可变参数的枚举:解释了为什么 enum 不能直接继承,并提供了用接口模拟可变行为的模式。
  • 条目 35:注解优于命名模式:展示了如何使用注解(Annotation)来替代传统的“标记接口”或“命名字符串”模式,@Test
  • 条目 36:坚持使用 Override 注解:强制编译器检查方法是否真的覆盖了父类方法,防止因拼写错误导致的方法隐藏。

第六部分:方法

  • 条目 43:返回零长度的数组或集合,而不是 null:让 API 的调用方更方便,避免了 NullPointerException 的风险。
  • 条目 44:为所有导出的 API 元素编写文档注释:强调了 JavaDoc 的重要性,并介绍了其规范。

第七部分:通用程序设计

  • 条目 48:谨慎地进行字符串拼接:在循环中,应优先使用 StringBuilder 而不是 操作符。
  • 条目 49:了解和使用库:鼓励开发者多使用 Java 标准库,而不是重复造轮子。
  • 条目 57:谨慎地进行优化:“过早的优化是万恶之源”,先让代码正确、清晰,然后在性能分析器(profiler)的指导下进行有针对性的优化。

第八部分:异常

  • 条目 57:只针对异常的情况才使用异常:不要用异常来控制正常的程序流程。
  • 条目 58:对可恢复的条件使用受检异常,对编程错误使用运行时异常
  • 条目 59:避免不必要地使用受检异常:过度使用受检异常会使 API 变得臃肿。

第九部分:并发

  • 条目 66:同步访问共享的可变数据:多线程编程的核心原则。
  • 条目 67:避免过度同步:过度同步会降低性能,并可能导致死锁。
  • 条目 68:优先使用 concurrent 工具类,而不是 synchronized:推荐使用 java.util.concurrent 包中的高级工具,如 ConcurrentHashMapExecutor 框架等。

第十部分:序列化

  • 条目 74:谨慎地实现 Serializable:序列化是一个复杂且容易出问题的特性,除非必要,否则不要轻易实现。
  • 条目 75:考虑使用自定义的序列化形式:默认的序列化形式往往不是最优的,应该仔细考虑如何序列化对象的状态。

为什么这本书如此重要?

  1. 权威性:作者 Joshua Bloch Java 语言标准库的设计者之一,书中的很多建议都源于 JDK 源码的设计经验和教训。
  2. 深度与广度:它涵盖了从基础的对象创建到高级的泛型、并发等几乎所有 Java 编程的关键领域。
  3. 实用性强:每个条目都像一篇小论文,有“问题描述”、“解决方案”和“,并且附有正反两方面的代码示例,易于理解和实践。
  4. 培养编程素养:它不仅仅教你“怎么做”,更教你“为什么这么做”,通过阅读,你会逐渐理解 Java 语言的设计哲学,培养出优秀的代码品味和严谨的工程思维。

如何阅读和使用这本书?

  • 不要试图一口气读完:它是一本工具书和参考指南,可以把它放在手边,遇到相关问题时,翻到对应的章节进行查阅和学习。
  • 精读并实践:对于与你当前工作最相关的章节(如泛型、并发、类设计),应该逐字逐句地精读,并尝试在自己的项目中应用这些原则。
  • 作为代码审查的标尺:当你或同事进行代码审查时,可以对照书中的条目,检查代码是否存在可以改进的地方。
  • 结合第三版阅读:虽然第二版非常经典,但如果你正在使用 Java 8 及更高版本,强烈建议你同时阅读或升级到 《Effective Java, Third Edition》,第三版增加了对 Lambda 表达式、Stream API、Optional 等新特性的深入探讨,并对许多条目进行了更新,使其与最新的 Java 生态保持同步。

《Effective Java, Second Edition》是每一位 Java 开发者(无论初学者还是资深专家)都应该反复阅读和珍藏的经典之作,它将深刻地影响你的编程习惯,帮助你写出更专业、更健壮、更高效的 Java 代码,即使现在有更新的第三版,第二版中关于面向对象设计、异常处理、并发编程等核心原则依然是颠扑不破的真理。

Effective第二版,Java编程核心要点何在?-图3
(图片来源网络,侵删)
分享:
扫描分享到社交APP
上一篇
下一篇