出版社: 机械工业出版社
原作名: Effective Java Second Edition
译者: 俞黎敏
出版年: 2009-1-1
页数: 287
定价: 52.00元
装帧: 平装
丛书: Sun公司核心技术丛书
ISBN: 9787111255833
内容简介 · · · · · ·
本书介绍了在Java编程中78条极具实用价值的经验规则,这些经验规则涵盖了大多数开发人员每天所面临的问题的解决方案。通过对Java平台设计专家所使用的技术的全面描述,揭示了应该做什么,不应该做什么才能产生清晰、健壮和高效的代码。
本书中的每条规则都以简短、独立的小文章形式出现,并通过例子代码加以进一步说明。本书内容全面,结构清晰,讲解详细。可作为技术人员的参考用书。
作者简介 · · · · · ·
Joshua Bloch是Google公司的首席Java架构师。是Jolt大奖的获得者。他曾是Sun公司的杰出工程师,和Transarc公司的高级系统设计师。Bloch曾带领团队设计和实现过无数的Java平台特性,包括JDK 5.0语言增强版和获奖的Java Collections Framework。他的著作还包括:《Java Puzzlers》、《Java Concurrency in Practive》等。
目录 · · · · · ·
序
前言
致谢
第1章 引言
第2章 创建和销毁对象
第1条:考虑用静态工厂方法代替构造器
第2条:遇到多个构造器参数时要考虑用构建器
第3条:用私有构造器或者枚举类型强化Singleton属性
第4条:通过私有构造器强化不可实例化的能力
第5条:避免创建不必要的对象
第6条:消除过期的对象引用
第7条:避免使用终结方法
第3章 对于所有对象都通用的方法
第8条:覆盖equals时请遵守通用约定
第9条:覆盖equals时总要覆盖hashCode
第10条:始终要覆盖toString
第11条:谨慎地覆盖clone
第12条:考虑实现Comparable接口
第4章 类和接口
第13条:使类和成员的可访问性最小化
第14条:在公有类中使用访问方法而非公有域
第15条:使可变性最小化
第16条:复合优先于继承
第17条:要么为继承而设计,并提供文档说明,要么就禁止继承
第18条:接口优于抽象类
第19条:接口只用于定义类型
第20条:类层次优于标签类
第21条:用函数对象表示策略
第22条:优先考虑静态成员类
第5章 泛型
第23条:请不要在新代码中使用原生态类型
第24条:消除非受检警告
第25条:列表优先于数组
第26条:优先考虑泛型
第27条:优先考虑泛型方法
第28条:利用有限制通配符来提升API的灵活性
第29条:优先考虑类型安全的异构容器
第6章 枚举和注解
第30条:用enum代替int常量
第31条:用实例域代替序数
第32条:用EnumSet代替位域
第33条:用EnumMap代替序数索引
第34条:用接口模拟可伸缩的枚举
第35条:注解优先于命名模式
第36条:坚持使用Override注解
第37条:用标记接口定义类型
第7章 方法
第38条:检查参数的有效性
第39条:必要时进行保护性拷贝
第40条:谨慎设计方法签名
第41条:慎用重载
第42条:慎用可变参数
第43条:返回零长度的数组或者集合,而不是:null
第44条:为所有导出的API元素编写文档注释
第8章 通用程序设计
第45条:将局部变量的作用域最小化
第46条:for-each循环优先于传统的for循环
第47条:了解和使用类库
第48条:如果需要精确的答案,请避免使用float和double
第49条:基本类型优先于装箱基本类型
第50条:如果其他类型更适合,则尽量避免使用字符串
第51条:当心字符串连接的性能
第52条:通过接口引用对象
第53条:接口优先于反射机制
第54条:谨慎地使用本地方法
第55条:谨慎地进行优化
第56条:遵守普遍接受的命名惯例
第9章 异常
第57条:只针对异常的情况才使用异常
第58条:对可恢复的情况使用受检异常,对编程错误使用运行时异常
第59条:避免不必要地使用受检的异常
第60条:优先使用标准的异常
第61条:抛出与抽象相对应的异常
第62条:每个方法抛出的异常都要有文档
第63条:在细节消息中包含能捕获失败的信息
第64条:努力使失败保持原子性
第65条:不要忽略异常
第10章 并发
第66条:同步访问共享的可变数据
第67条:避免过度同步
第68条:executor和task优先干线程
第69条:并发工具优先于wait和notify
第70条:线程安全性的文档化
第71条:慎用延迟初始化
第72条:不要依赖于线程调度器
第73条:避免使用线程组
第11章 序列化
第74条:谨慎地实现Serializable接口
第75条:考虑使用自定义的序列化形式
第76条:保护性地编写readObject方法
第77条:对于实例控制,枚举类型优先于readResolve
第78条:考虑用序列化代理代替序列化实例
附录 第1版与第2版条目对照
中英文术语对照
参考文献
· · · · · · (收起)
原文摘录 · · · · · · ( 全部 )
-
Item 57: Use exceptions only for exceptional conditions Item 58: Use checked exceptions for recoverable conditions and runtime exceptions for programming errors Item 59: Avoid unnecessary use of checked exceptions Item 60: Favor the use of standard exceptions Item 61: Throw exceptions appropriate to the abstraction Item 62: Document all exceptions thrown by each method Item 63: Include failure-capture information in detail messages Item 64: Strive for failure atomicity Item 65: Don’t ignore exceptions (查看原文) —— 引自第241页 -
Errors are reserved for use by the JVM to indicate resource defi-ciencies, invariant failures, or other conditions that make it impossible to continue execution (查看原文) —— 引自第241页
> 全部原文摘录
丛书信息
喜欢读"Effective java 中文版(第2版)"的人也喜欢的电子书 · · · · · ·
喜欢读"Effective java 中文版(第2版)"的人也喜欢 · · · · · ·
Effective java 中文版(第2版)的话题 · · · · · · ( 全部 条 )



Effective java 中文版(第2版)的书评 · · · · · · ( 全部 48 条 )


看书前不建议直接看评论

Effective Java (Part 1 - Creating and Destroying Objects)
> 更多书评 48篇
-
Dylan阿风 (迷失的人迷失了相逢的人会再相逢)
线程安全性的几种级别: 1.不可变的(immutable)--这个类的实例是不变的,所以不需要外部的同步。 例如:String、Long和BigInteger 2.无条件的线程安全(unconditionally thread-safe)--这个类的实例是可变的,但是这个类有着足够的内部同步,所以它的实例可以被并发使用,无需任何外部同步。 例如:Random和ConcurrentHashMap 3.有条件的线程安全(conditionally thread-safe)--除了有些方法为进行安全的并发而使用需要外部同步之...2013-03-15 14:30:11 2人喜欢
线程安全性的几种级别: 1.不可变的(immutable)--这个类的实例是不变的,所以不需要外部的同步。 例如:String、Long和BigInteger 2.无条件的线程安全(unconditionally thread-safe)--这个类的实例是可变的,但是这个类有着足够的内部同步,所以它的实例可以被并发使用,无需任何外部同步。 例如:Random和ConcurrentHashMap 3.有条件的线程安全(conditionally thread-safe)--除了有些方法为进行安全的并发而使用需要外部同步之外,这种线程安全级别与无条件的线程安全相同。 例如:Collections.synchronized包装返回的集合,它们的迭代器(iterator)要求外部同步 4.非线程安全(not thread-safe)--这个实例是可变的。为了并发地使用它们,客户必须利用自己选择的外部同步包围每个方法调用(或者调用序列) 例如:ArrayList和HashMap 5.线程对立的(thread-hostie)--这个类不能安全地被多个线程并发使用,即使所有的方法调用都被外部同步包围。
回应 2013-03-15 14:30:11 -
WuQifu (喜欢买书的软件工程师~)
本想给这本书4星的,因为感觉没有Scott Meyers的《Effective C++》、《More Effective C++》、《Effective STL》系列写得好;考虑到Java学习上只此一本《Effective Java》还是给5星吧。毕竟这本书也还是很值得一读的! 抄录一些笔记,空白的条目表示没看明白,以后有新的理解再补充。 第一章 引言 一, 代码应该被重用,而不是被拷贝。 第二章 创建和销毁对象 一,考虑用静态工厂方法代替构造器 public static Boolean valueOf(...2011-05-15 20:19:24 2人喜欢
本想给这本书4星的,因为感觉没有Scott Meyers的《Effective C++》、《More Effective C++》、《Effective STL》系列写得好;考虑到Java学习上只此一本《Effective Java》还是给5星吧。毕竟这本书也还是很值得一读的! 抄录一些笔记,空白的条目表示没看明白,以后有新的理解再补充。 第一章 引言 一, 代码应该被重用,而不是被拷贝。 第二章 创建和销毁对象 一,考虑用静态工厂方法代替构造器 public static Boolean valueOf(boolean b) { return b ? Boolean.TRUE : Boolean.FALSE; } 静态工厂方法能够为重复的调用返回相同的对象。 静态工厂惯用名称:valueOf, of, getInstance, newInstance, getType, newType. 二, 遇到多个构造器参数时要考虑用builder 三,用私有构造器或者枚举类型强化Singleton属性 1,public class Elvis { public static final Elvis INSTANCE = new Elvis(); private Elvis() { .... } public void leaveTheBuilding() {...} } 2, public class Elvis { private static final Elvis INSTANCE = new Elvis(); private Elvis() { ... } public static Elvis getInstance() { return INSTANCE; } public void leaveTheBuilding() { ... } } 3, 单元素的枚举类型已经成为实现Singleton最佳方法 public enum Elvis { INSTANCE; public void leaveTheBuilding() { ... } } 四,通过私有构造器强化不可实例化的能力 只包含静态方法和静态域的工具类(utility class)实例对它没任何意义,只要让这个类构造器私有就可以保证不会被实例化。 public class UtilityClass { private UtilityClass() { throw new AssertionError(); } 副作用:这个类不能被继承。所有的构造器都必须显示或隐式地调用超类的构造器。 五,避免创建不必要的对象 构造器在每次被调用时都会创建一个新的对象。可以使用静态工厂方法代替构造器,以避免创建不必要的对象。例:Boolean.valueOf(String)。 静态初始化,只需初始化一次。 延迟初始化。 六,消除过期的对象引用 只要是类是自己管理内存,程序员就应该警惕内存泄漏。 七,比用使用终结方法 终结方法(finalizer)通常是不可以预测的,也是很危险的。终结方法的缺点在于不能保证会被及时地执行。 在C++中,析构器是回收一个对象所占资源的常规方法。Java中,一般用try-finally完成类似的工作。 第三章 对于所有对象都通用的方法 八,覆盖equals时请遵守通用约定 ==比较的是引用,equals比较的是值! 九,覆盖equals时总要覆盖hashcode @Override public boolean equals(Object O) { ... } @Override public int hashCode() { ... } 相等的(equals)的对象必须具有相等的hash code。不相等的两个对象,hash code有可能相等。 Eclispe提供了代码生成工具(Source->Generates hashCode() and equals()...) 十,始终要覆盖toString @Override public String toString() { ... } 十一,谨慎地覆盖clone()方法 public interface Cloneable { } 如果一个类实现了Cloneable,Object的clone方法就会返回该对象的逐域拷贝,否则就会抛出CloneNotSupportedException. clone()就是另一个构造器;你必须确保它不会伤害到原始的对象,并确保正确地创建被克隆对象中的约束条件。(深度拷贝,deep copy) 无需调用构造器就可以创建对象。 协变返回类型(covariant return type),override方法的返回类型可以是被覆盖方法返回类型的子类型。 所有实现Cloneable接口的类都应该用一个公有方法覆盖clone。此方法首先调用super.clone(),然后clone自身域。 @Override public Stack clone() { try { Stack result = (Stack)super.clone(); result.elements = elements.clone(); return result; } catch (CloneNotSupportedException e) { throw new AssertionError(); } } 另一个实现对象拷贝的办法是提供一个拷贝构造器或拷贝工厂: public Yum(Yum yum) copy ctor public static Yum newInstance(Yum yum); copy factory 十二,考虑实现Comparable接口 类实现了Comparable接口,就表明它的实例具有内在的排序关系。 public interface Comparable<T> { int compareTo(T t); } 当该对象小于、等于或大于指定对象的时候,分别返回一个负整数、零或正整数。 第四章 类和接口 十三, 使类和成员的可访问性最小化 private, package-private, protected, public 十四,在公有类中使用访问方法而非公有域 十五,使可变性最小化 十六,组合优先于继承 实现继承(implementation inheritance), 接口继承(interface inheritance) 组合(composition), 转发方法(forwarding method) 包装类(wrapper class)-->Decorator模式 十七,要么为继承而设计并提供文档说明,要么就禁止继承 十八,接口优于抽象类 抽象类允许包含某些方法的实现;接口不允许。 为实现抽象类定义的类型,类必须成为抽象类的一个子类,Java只允许单继承;可以implement多个接口 十九,接口只用于定义类型 静态导入(static import):JUnit,ass ertEquals() 二十,类层次优于标签类 二十一,用函数对象表示策略 class StringLengthComparator { public int compare(String s1, String s2) { return s1.length() - s2.length(); } } StringLengthComparator没有域是无状态的,因此非常适合成为Singleton。 class StringLengthComparator { private StringLengthComparator() { } public static final StringLengthComparator INSTANCE = new StringLengthComparator(); public int compare(String s1, String s2) { return s1.length() - s2.length(); } } public interface Comparator<T> { public int compare(T t1, T t2); } Arrays.sort(stringArray, new Comparator<String>() { public int compare(String s1, String s2) { return s1.length() - s2.length(); } }; 可以将函数对象存储到一个私有的静态final域中,并重用。 class Host { private static class StringLengthComparator implements Comparator<String>, Serializable { public int compare(String s1, String s2) { return s1.length() - s2.length(); } } public static final Comparator<String> STRING_LENGTH_COMPARATOR = new StringLengthComparator(); //..... } 函数指针的主要用途就是实现策略(Strategy)模式。Java中声明一个接口表示策略,并且为每个具体策略声明一个实现了该接口的类。例:Arrays.sort(array, comparator); 二十二,优先考虑静态成员类 嵌套类有四种:静态成员类,非静态成员类,匿名类,局部类。 非静态成员类的每个实例都隐含着与一个外围实例相关联 匿名类一种常见用法是动态地创建函数对象;另一种用法是创建过程对象,比如Runnable,Thread或者TimerTask实例;第三种常见的用法是在静态工厂方法的内部。 第五章 泛型 二十三,不要在新代码中使用原生态类型 二十四,消除非受检警告 @SuppressWarnings("unchecked") 二十五,List优先于数组 二十六,优先考虑泛型 二十七,优先考虑泛型方法 二十八,利用有限制通配符来提升API的灵活性 二十九,优先考虑类型安全的异构容器 第六章 枚举和注解 三十,用enum代替int常量 三十一,用实例域代替序数 public enum Ensemble { SOLO(1), DUET(2), TRIO(3), QUARTET(4); private final int numberOfMusicians; Ensemble(int size) { this.numberOfMusicians = size; } public int numberOfMusicians() { return numberOfMusicians; } } 三十二,用EnumSet代替位域 三十三,用EnumMap代替序数索引 三十四,用接口模拟可伸缩的枚举 三十五,注解优先于命名模式 三十六,坚持用Override注解 三十七,用标记接口定义类型 标记接口(marker interface)是没有包含方法声明的接口。例:Serializable 第七章 方法 三十八,检查参数有效性 在方法体得开头处检查参数。 三十九,必要时进行保护性拷贝 四十,谨慎设计方法签名 谨慎选择方法名;避免过长参数列表;参数类型优先使用接口而非具体类; 对于boolean参数,优先使用两个元素的枚举类型: public enum TemperatureScale { FAHRENHEIT, CELSIUS } 四十一,慎用重载 overload方法的选择是静态的,overridden方法的选择是动态。 四十二,慎用可变参数 四十三,返回零长度的数组或者集合而不是null Collections.emptySet, emptyList, emptyMap private final List<Cheese> cheesesInStock = ...; public List<Cheese> getCheeseList() { if (cheeseInStock.isEmpty()) return Collections.emptyList(); else return new ArrayList<Cheese>(cheeseInStock); } } 四十四,为所有导出的API元素编写文档注释 第八章 通用程序设计 四十五,将局部变量的作用域最小化 四十六,for-each循环优先于传统的for循环 for (Iterator i = c.iterator(); i.hasNext(); ) { doSomething((Element)i.next()); // i.remove(); } public interface Iterable<E> { Iterator<E> iterator(); } 三种情况下无法使用for-each循环:过滤,转换,平行迭代。 四十七,了解和使用类库 java.lang.*, java.util.*, Collections Framework 四十八,如果需要精确的答案,请避免使用float和double BigDecimal 四十九,基本类型优先于装箱类型 永远不要用==做相等测试!Object.equals(object); 五十,如果其他类型更适合,则避免使用字符串 五十一,需要连接字符串时,用StringBuilder代替String 五十二,优先使用接口而非类来引用对象 五十三,接口优先于反射机制 五十四,谨慎地使用本地方法 五十五,谨慎地进行优化 必须在设计时考虑性能问题;使用性能剖析工具探测性能瓶颈 五十六,遵守普遍接受的命名惯例 第九章 异常 五十七,只针对异常的情况才使用异常 五十八,对可恢复的情况使用受检情况,对编程错误使用运行时异常 五十九,避免不必要地使用受检的异常 六十,优先使用标准的异常 六十一,抛出与抽象相对应的异常 六十二,每个方法抛出的异常都要有文档 六十三,在细节消息中包含能捕获失败的信息 六十四,努力使失败保持原子性 六十五,不要忽略异常 第十章 并发 六十六,同步访问共享的可变数据 六十七,避免过度同步 六十八,executor和task优先于线程 六十九,并发工具优先于wait和notify 七十,线程安全性的文档化 七十一,延迟延迟初始化 七十二,不要依赖于线程调度器 七十三,避免使用线程组 第十一章 序列化 七十四,谨慎地实现Serializable接口 七十五,考虑使用自定义的序列化形式 七十六,保护性地编写readObject方法 七十七,对于实例控制,枚举类型优先于readResolve 七十八,考虑用序列化代理代替序列化实例
回应 2011-05-15 20:19:24 -
amare小霸王 (Li Yingjun)
第一条:考虑用静态工厂方法代替构造器 静态工厂方法与构造器不同的第一大优势在于,它们有名称 静态工厂方法与构造器不同的第二大优势在于,不必在每次调用它们的时候都创建一个新对象;静态工厂方法能够为重复的调用返回相同对象。 静态工厂方法与构造器不同的第三大优势在于,它们可以返回原返回类型的任何子类型的对象 静态工厂方法与构造器不同的第四大优势在于,在创建参数化类型实例的时候,它们使代码变得更加简洁2022-05-21 17:39:40
-
WuQifu (喜欢买书的软件工程师~)
本想给这本书4星的,因为感觉没有Scott Meyers的《Effective C++》、《More Effective C++》、《Effective STL》系列写得好;考虑到Java学习上只此一本《Effective Java》还是给5星吧。毕竟这本书也还是很值得一读的! 抄录一些笔记,空白的条目表示没看明白,以后有新的理解再补充。 第一章 引言 一, 代码应该被重用,而不是被拷贝。 第二章 创建和销毁对象 一,考虑用静态工厂方法代替构造器 public static Boolean valueOf(...2011-05-15 20:19:24 2人喜欢
本想给这本书4星的,因为感觉没有Scott Meyers的《Effective C++》、《More Effective C++》、《Effective STL》系列写得好;考虑到Java学习上只此一本《Effective Java》还是给5星吧。毕竟这本书也还是很值得一读的! 抄录一些笔记,空白的条目表示没看明白,以后有新的理解再补充。 第一章 引言 一, 代码应该被重用,而不是被拷贝。 第二章 创建和销毁对象 一,考虑用静态工厂方法代替构造器 public static Boolean valueOf(boolean b) { return b ? Boolean.TRUE : Boolean.FALSE; } 静态工厂方法能够为重复的调用返回相同的对象。 静态工厂惯用名称:valueOf, of, getInstance, newInstance, getType, newType. 二, 遇到多个构造器参数时要考虑用builder 三,用私有构造器或者枚举类型强化Singleton属性 1,public class Elvis { public static final Elvis INSTANCE = new Elvis(); private Elvis() { .... } public void leaveTheBuilding() {...} } 2, public class Elvis { private static final Elvis INSTANCE = new Elvis(); private Elvis() { ... } public static Elvis getInstance() { return INSTANCE; } public void leaveTheBuilding() { ... } } 3, 单元素的枚举类型已经成为实现Singleton最佳方法 public enum Elvis { INSTANCE; public void leaveTheBuilding() { ... } } 四,通过私有构造器强化不可实例化的能力 只包含静态方法和静态域的工具类(utility class)实例对它没任何意义,只要让这个类构造器私有就可以保证不会被实例化。 public class UtilityClass { private UtilityClass() { throw new AssertionError(); } 副作用:这个类不能被继承。所有的构造器都必须显示或隐式地调用超类的构造器。 五,避免创建不必要的对象 构造器在每次被调用时都会创建一个新的对象。可以使用静态工厂方法代替构造器,以避免创建不必要的对象。例:Boolean.valueOf(String)。 静态初始化,只需初始化一次。 延迟初始化。 六,消除过期的对象引用 只要是类是自己管理内存,程序员就应该警惕内存泄漏。 七,比用使用终结方法 终结方法(finalizer)通常是不可以预测的,也是很危险的。终结方法的缺点在于不能保证会被及时地执行。 在C++中,析构器是回收一个对象所占资源的常规方法。Java中,一般用try-finally完成类似的工作。 第三章 对于所有对象都通用的方法 八,覆盖equals时请遵守通用约定 ==比较的是引用,equals比较的是值! 九,覆盖equals时总要覆盖hashcode @Override public boolean equals(Object O) { ... } @Override public int hashCode() { ... } 相等的(equals)的对象必须具有相等的hash code。不相等的两个对象,hash code有可能相等。 Eclispe提供了代码生成工具(Source->Generates hashCode() and equals()...) 十,始终要覆盖toString @Override public String toString() { ... } 十一,谨慎地覆盖clone()方法 public interface Cloneable { } 如果一个类实现了Cloneable,Object的clone方法就会返回该对象的逐域拷贝,否则就会抛出CloneNotSupportedException. clone()就是另一个构造器;你必须确保它不会伤害到原始的对象,并确保正确地创建被克隆对象中的约束条件。(深度拷贝,deep copy) 无需调用构造器就可以创建对象。 协变返回类型(covariant return type),override方法的返回类型可以是被覆盖方法返回类型的子类型。 所有实现Cloneable接口的类都应该用一个公有方法覆盖clone。此方法首先调用super.clone(),然后clone自身域。 @Override public Stack clone() { try { Stack result = (Stack)super.clone(); result.elements = elements.clone(); return result; } catch (CloneNotSupportedException e) { throw new AssertionError(); } } 另一个实现对象拷贝的办法是提供一个拷贝构造器或拷贝工厂: public Yum(Yum yum) copy ctor public static Yum newInstance(Yum yum); copy factory 十二,考虑实现Comparable接口 类实现了Comparable接口,就表明它的实例具有内在的排序关系。 public interface Comparable<T> { int compareTo(T t); } 当该对象小于、等于或大于指定对象的时候,分别返回一个负整数、零或正整数。 第四章 类和接口 十三, 使类和成员的可访问性最小化 private, package-private, protected, public 十四,在公有类中使用访问方法而非公有域 十五,使可变性最小化 十六,组合优先于继承 实现继承(implementation inheritance), 接口继承(interface inheritance) 组合(composition), 转发方法(forwarding method) 包装类(wrapper class)-->Decorator模式 十七,要么为继承而设计并提供文档说明,要么就禁止继承 十八,接口优于抽象类 抽象类允许包含某些方法的实现;接口不允许。 为实现抽象类定义的类型,类必须成为抽象类的一个子类,Java只允许单继承;可以implement多个接口 十九,接口只用于定义类型 静态导入(static import):JUnit,ass ertEquals() 二十,类层次优于标签类 二十一,用函数对象表示策略 class StringLengthComparator { public int compare(String s1, String s2) { return s1.length() - s2.length(); } } StringLengthComparator没有域是无状态的,因此非常适合成为Singleton。 class StringLengthComparator { private StringLengthComparator() { } public static final StringLengthComparator INSTANCE = new StringLengthComparator(); public int compare(String s1, String s2) { return s1.length() - s2.length(); } } public interface Comparator<T> { public int compare(T t1, T t2); } Arrays.sort(stringArray, new Comparator<String>() { public int compare(String s1, String s2) { return s1.length() - s2.length(); } }; 可以将函数对象存储到一个私有的静态final域中,并重用。 class Host { private static class StringLengthComparator implements Comparator<String>, Serializable { public int compare(String s1, String s2) { return s1.length() - s2.length(); } } public static final Comparator<String> STRING_LENGTH_COMPARATOR = new StringLengthComparator(); //..... } 函数指针的主要用途就是实现策略(Strategy)模式。Java中声明一个接口表示策略,并且为每个具体策略声明一个实现了该接口的类。例:Arrays.sort(array, comparator); 二十二,优先考虑静态成员类 嵌套类有四种:静态成员类,非静态成员类,匿名类,局部类。 非静态成员类的每个实例都隐含着与一个外围实例相关联 匿名类一种常见用法是动态地创建函数对象;另一种用法是创建过程对象,比如Runnable,Thread或者TimerTask实例;第三种常见的用法是在静态工厂方法的内部。 第五章 泛型 二十三,不要在新代码中使用原生态类型 二十四,消除非受检警告 @SuppressWarnings("unchecked") 二十五,List优先于数组 二十六,优先考虑泛型 二十七,优先考虑泛型方法 二十八,利用有限制通配符来提升API的灵活性 二十九,优先考虑类型安全的异构容器 第六章 枚举和注解 三十,用enum代替int常量 三十一,用实例域代替序数 public enum Ensemble { SOLO(1), DUET(2), TRIO(3), QUARTET(4); private final int numberOfMusicians; Ensemble(int size) { this.numberOfMusicians = size; } public int numberOfMusicians() { return numberOfMusicians; } } 三十二,用EnumSet代替位域 三十三,用EnumMap代替序数索引 三十四,用接口模拟可伸缩的枚举 三十五,注解优先于命名模式 三十六,坚持用Override注解 三十七,用标记接口定义类型 标记接口(marker interface)是没有包含方法声明的接口。例:Serializable 第七章 方法 三十八,检查参数有效性 在方法体得开头处检查参数。 三十九,必要时进行保护性拷贝 四十,谨慎设计方法签名 谨慎选择方法名;避免过长参数列表;参数类型优先使用接口而非具体类; 对于boolean参数,优先使用两个元素的枚举类型: public enum TemperatureScale { FAHRENHEIT, CELSIUS } 四十一,慎用重载 overload方法的选择是静态的,overridden方法的选择是动态。 四十二,慎用可变参数 四十三,返回零长度的数组或者集合而不是null Collections.emptySet, emptyList, emptyMap private final List<Cheese> cheesesInStock = ...; public List<Cheese> getCheeseList() { if (cheeseInStock.isEmpty()) return Collections.emptyList(); else return new ArrayList<Cheese>(cheeseInStock); } } 四十四,为所有导出的API元素编写文档注释 第八章 通用程序设计 四十五,将局部变量的作用域最小化 四十六,for-each循环优先于传统的for循环 for (Iterator i = c.iterator(); i.hasNext(); ) { doSomething((Element)i.next()); // i.remove(); } public interface Iterable<E> { Iterator<E> iterator(); } 三种情况下无法使用for-each循环:过滤,转换,平行迭代。 四十七,了解和使用类库 java.lang.*, java.util.*, Collections Framework 四十八,如果需要精确的答案,请避免使用float和double BigDecimal 四十九,基本类型优先于装箱类型 永远不要用==做相等测试!Object.equals(object); 五十,如果其他类型更适合,则避免使用字符串 五十一,需要连接字符串时,用StringBuilder代替String 五十二,优先使用接口而非类来引用对象 五十三,接口优先于反射机制 五十四,谨慎地使用本地方法 五十五,谨慎地进行优化 必须在设计时考虑性能问题;使用性能剖析工具探测性能瓶颈 五十六,遵守普遍接受的命名惯例 第九章 异常 五十七,只针对异常的情况才使用异常 五十八,对可恢复的情况使用受检情况,对编程错误使用运行时异常 五十九,避免不必要地使用受检的异常 六十,优先使用标准的异常 六十一,抛出与抽象相对应的异常 六十二,每个方法抛出的异常都要有文档 六十三,在细节消息中包含能捕获失败的信息 六十四,努力使失败保持原子性 六十五,不要忽略异常 第十章 并发 六十六,同步访问共享的可变数据 六十七,避免过度同步 六十八,executor和task优先于线程 六十九,并发工具优先于wait和notify 七十,线程安全性的文档化 七十一,延迟延迟初始化 七十二,不要依赖于线程调度器 七十三,避免使用线程组 第十一章 序列化 七十四,谨慎地实现Serializable接口 七十五,考虑使用自定义的序列化形式 七十六,保护性地编写readObject方法 七十七,对于实例控制,枚举类型优先于readResolve 七十八,考虑用序列化代理代替序列化实例
回应 2011-05-15 20:19:24
-
amare小霸王 (Li Yingjun)
第一条:考虑用静态工厂方法代替构造器 静态工厂方法与构造器不同的第一大优势在于,它们有名称 静态工厂方法与构造器不同的第二大优势在于,不必在每次调用它们的时候都创建一个新对象;静态工厂方法能够为重复的调用返回相同对象。 静态工厂方法与构造器不同的第三大优势在于,它们可以返回原返回类型的任何子类型的对象 静态工厂方法与构造器不同的第四大优势在于,在创建参数化类型实例的时候,它们使代码变得更加简洁2022-05-21 17:39:40
论坛 · · · · · ·
java100套毕设 链接:https://pan.baidu.com/s/1R9... | 来自冰雨 | 2018-10-24 14:35:56 | |
Effective Java Second Edition中文版勘误列表专用贴 | 来自YuLimin | 2 回应 | 2016-02-08 14:24:02 |
极品 | 来自半兽人 | 2010-11-03 09:43:57 | |
即使看过第一版也值得再看第二版 | 来自我有分寸 | 2010-10-25 22:31:15 | |
如何写出符合Java特性的代码?如何写出符合英语特... | 来自Bourne | 1 回应 | 2010-08-23 00:25:10 |
> 浏览更多话题
这本书的其他版本 · · · · · · ( 全部13 )
-
Addison-Wesley (2008)9.3分 281人读过
-
机械工业出版社 (2003)8.9分 1091人读过
-
机械工业出版社 (2018)9.3分 250人读过
-
Addison-Wesley Professional (2018)9.7分 163人读过
以下书单推荐 · · · · · · ( 全部 )
- 豆瓣评分>9的计算机图书 (whg)
- 闲着没事读读书(四) (鹿小羽)
- Java修炼之道 (威廉他)
- 交互设计师养成书单 (LimboMinaïss)
- 图书类Jolt大奖和生产力大奖 (zpp)
谁读这本书?
二手市场
订阅关于Effective java 中文版(第2版)的评论:
feed: rss 2.0
0 有用 Ke Bo 2011-11-12 13:14:23
进阶
2 有用 一只黑眼睛看着大千世界 2016-03-07 21:50:23
保持Effective系列水平,对Java进阶提升很有帮助。可惜内容比较旧了,中文翻译也不太理想。 (2015.6.2jd)
0 有用 丸子(^.^)v 2016-06-24 12:43:17
为了面试 也是豁出去了 @@
5 有用 lili 2015-08-20 14:53:43
这种书还是要看的,但是要批判的看
0 有用 jason 2011-11-01 15:16:14
用了近两个整天较仔细的读完了这本书,感觉尤其是新手都应该把这本书读一遍吧。
0 有用 更换呼吸 2021-12-18 21:38:46
必读。但又不怎么用得到。矛盾
0 有用 天很蓝 2021-11-28 22:30:23
补充记录~
0 有用 阿里阿里巴巴 2021-10-08 15:09:24
不太好理解,可能是翻译有问题
0 有用 阅微草堂 2021-09-27 23:01:33
java系统的体系化,业务需求的功能的完成,语言的设计和实现,性能的提升。分层次的梳理和学习。
0 有用 迷糊蛋儿 2021-08-22 08:27:26
茅塞顿开