Effective Java 41 Use overloading judiciously
The choice of which overloading to invoke is made at compile time.
// Broken! - What does this program print?
public class CollectionClassifier {
public static String classify(Set<?> s) {
return "Set";
}
public static String classify(List<?> lst) {
return "List";
}
public static String classify(Collection<?> c) {
return "Unknown Collection";
}
public static void main(String[] args) {
Collection<?>[] collections = {
new HashSet<String>(),
new ArrayList<BigInteger>(),
new HashMap<String, String>().values()
};
for (Collection<?> c : collections)
System.out.println(classify(c));
// the result will prints three times "Unknown Collection"
}
}
Selection among overloaded methods is static, while selection among overridden methods is dynamic.
The compile-time type of an object has no effect on which method is executed when an overridden method is invoked; the "most specific" overriding method always gets executed.
class Wine {
String name() { return "wine"; }
}
class SparklingWine extends Wine {
@Override String name() { return "sparkling wine"; }
}
class Champagne extends SparklingWine {
@Override String name() { return "champagne"; }
}
public class Overriding {
public static void main(String[] args) {
Wine[] wines = {
new Wine(), new SparklingWine(), new Champagne()
};
for (Wine wine : wines)
System.out.println(wine.name());
// This will print "wine" "sparking wine" "Champagne"
}
}
Principle
- A safe, conservative policy is never to export two overloadings with the same number of parameters.
public class SetList {
public static void main(String[] args) {
Set<Integer> set = new TreeSet<Integer>();
List<Integer> list = new ArrayList<Integer>();
for (int i = -3; i < 3; i++) {
set.add(i);
list.add(i);
}
for (int i = 0; i < 3; i++) {
set.remove(i);
list.remove(i);
}
System.out.println(set + " " + list);
// This will prints [-3, -2, -1] [-2, 0, 2]
}
}
The call to set.remove(i)selects the overloading remove(E), where E is the element type of the set (Integer), and autoboxes I from int to Integer.
The call to list.remove(i), on the other hand, selects the overloading remove(int i), which removes the element at the specified position from a list.
2. The standard way to ensure behavior of the types of the same super class or interface as the parameter of a method is to have the more specific overloading forward to the more general.
public boolean contentEquals(StringBuffer sb) {
return contentEquals((CharSequence) sb);
}
Summary
You should generally refrain from overloading methods with multiple signatures that have the same number of parameters. You can name the method with same prefix rather than overloading the write method. Such as, these variants of ObjectOutputStream have signatures like writeBoolean(boolean), writeInt(int), and writeLong(long).
In some cases, especially where constructors are involved, it may be impossible to follow this advice. In that case, you should at least avoid situations where the same set of parameters can be passed to different overloadings by the addition of casts. In this case you have the option of exporting static factories instead of constructors (Item 1).
If such a situation cannot be avoided, for example, because you are retrofitting an existing class to implement a new interface, you should ensure that all overloadings behave identically when passed the same parameters.
Effective Java 41 Use overloading judiciously的更多相关文章
- Effective Java 11 Override clone judiciously
Principles If you override the clone method in a nonfinal class, you should return an object obtaine ...
- Effective Java 42 Use varargs judiciously
Implementation theory The varargs facility works by first creating an array whose size is the number ...
- Effective Java 74 Implement Serializable judiciously
Disadvantage of Serializable A major cost of implementing Serializable is that it decreases the flex ...
- Effective Java Index
Hi guys, I am happy to tell you that I am moving to the open source world. And Java is the 1st langu ...
- 《Effective Java》读书笔记 - 7.方法
Chapter 7 Methods Item 38: Check parameters for validity 直接举例吧: /** * ...其他的被我省略了 * @throws Arithmet ...
- Effective Java 第三版——41.使用标记接口定义类型
Tips <Effective Java, Third Edition>一书英文版已经出版,这本书的第二版想必很多人都读过,号称Java四大名著之一,不过第二版2009年出版,到现在已经将 ...
- Effective Java 目录
<Effective Java>目录摘抄. 我知道这看起来很糟糕.当下,自己缺少实际操作,只能暂时摘抄下目录.随着,实践的增多,慢慢填充更多的示例. Chapter 2 Creating ...
- 【Effective Java】阅读
Java写了很多年,很惭愧,直到最近才读了这本经典之作<Effective Java>,按自己的理解总结下,有些可能还不够深刻 一.Creating and Destroying Obje ...
- [Effective Java]第八章 通用程序设计
声明:原创作品,转载时请注明文章来自SAP师太技术博客( 博/客/园www.cnblogs.com):www.cnblogs.com/jiangzhengjun,并以超链接形式标明文章原始出处,否则将 ...
随机推荐
- [linux]重拾linux
起因 因为想重拾起linux,同时需要用docker起几个镜像,用来学习网络知识.本来想直接去阿里云上买,后来一想自己机器上,起一个linux是个不错的选择,毕竟不花钱! 还可以用来做本地测试,学习使 ...
- sublime 插件zen coding
sublime的插件Zen Coding是一个编写html的神器,现在已经更名为Emmet了. 在sublime中的package需要搜索的是Emmet 相关网站: 官网 Zen Coding: 一种 ...
- JavaScript异常捕获
理论准备 ★ 异常捕获 △ 异常:当JavaScript引擎执行JavaScript代码时,发生了错误,导致程序停止运行: △ 异常抛出:当异常产生,并且这个异常生成一个错误信息: △ 异常捕获: ...
- H5案例学习笔记
★基础篇 增加主体结构元素
- .net 读书笔记
好书不能只读一遍,这两天又翻看了一遍<你必须知道的.NET>,重温了下基础,重温了下经典,简单记录了下来. 内存分配:CLR 管理内存的区域,主要有三块,分别为: 线程的堆栈,用于分配值类 ...
- 自学silverlight 5.0
这是一个silverlight游戏:http://keleyi.com/keleyi/phtml/silverlight/ 接了个单子,非要用Silverlight 5来作一个项目,之前从来没接触过这 ...
- HTTP请求中的Body构建——.NET客户端调用JAVA服务进行文件上传
PS:今日的第二篇,当日事还要当日毕:) http的POST请求发送的内容在Body中,因此有时候会有我们自己构建body的情况. JAVA使用http—post上传file时,spring框架中 ...
- 重新想象 Windows 8 Store Apps (36) - 通知: Tile 详解
[源码下载] 重新想象 Windows 8 Store Apps (36) - 通知: Tile 详解 作者:webabcd 介绍重新想象 Windows 8 Store Apps 之 通知 Tile ...
- Studio for Winforms FlexGrid: 创建分类汇总
C1FlexGrid.Subtotal方法可以增加包含普通(非小计)行的汇总数据的分类汇总行. 分类汇总支持分层聚合.例如,如果你的表格包含销售数据,你可能会通过产品.地区和推销员来小计一下以得出总的 ...
- Install gocode
1. D:\AWS_workspace\DAAS_Go>go get -u -ldflags -H=windowsgui github.com/nsf/gocode 2. Then gocode ...