深入理解abstract class与interface
abstract class 和 interface 是 Java 里定义抽象类型的两种机制,也因此赋予了语言强大的面向对象能力。二者很像,有时还能互换,所以不少人选型很随意。 其实差别不小:选哪一个,往往反映出你对问题领域本质、对设计意图的理解是否站得住。下面按语法、编程和设计理念三层来拆。 一、…
abstract class 和 interface 是 Java 里定义抽象类型的两种机制,也因此赋予了语言强大的面向对象能力。二者很像,有时还能互换,所以不少人选型很随意。 其实差别不小:选哪一个,往往反映出你对问题领域本质、对设计意图的理解是否站得住。下面按语法、编程和设计理念三层来拆。 一、…
消息摘要有唯一性和不可逆:同样的输入得到同样的摘要,很难从摘要反推原文。MD5 常被拿来做校验,旧系统里也用来处理用户口令(现代密码存储应使用专门的慢哈希,这里按原文给出一个简洁实现)。 下面这个 StringUtil 把任意字符串编成 32 位十六进制 MD5。 一、实现类 package tes…
应用里常有周期性工作,比如每 5 分钟检查一次新邮件。这类任务用 java.util.Timer 最省事:它自己维护调度线程,不必手写循环休眠。 Timer 也适合延迟执行(类似电视的延时关机)。多个线程可以共用一个 Timer,它内部是同步的,一般不必再包一层锁。 一、周期调度 下面这段每 5 分…
类是对象的模板,抽象类和接口可以看成具体类的模板。接口从某种角度看是一种特殊的抽象类,相似处很多,选择时容易混。先看相同点,再看各自擅长什么。 使用引用变量时,尽量用类结构的抽象层,让方法的定义和实现分离,代码才能松散耦合。 对比 抽象类 接口 实例化 不能 new 不能 new 抽象方法 可以有,…
抽象类里可以有抽象方法,也可以有已经实现的方法;接口(interface)更“抽象”:传统上它规定一个类必须做什么,而不规定怎么做。 接口用 interface 声明,可以看成一种特殊的抽象类。Java 8 起接口也可以有 default / static 方法,Java 9 还可以有 privat…
自上而下的继承层次里,越靠上的类越通用,甚至更抽象。祖先类往往只包含最基本的成员,人们只把它当作派生其他类的基类,而不会拿它来 new 对象。方法也可以只给出定义、不写实现,交给子类按具体需求去完成。 这种只有定义、没有方法体(没有 {})的方法叫做抽象方法。含有一个或多个抽象方法的类必须声明为抽象…
Java 允许在一个类(或方法、语句块)内部再定义另一个类,称为内部类(Inner Class),有时也叫嵌套类(Nested Class)。 内部类和外层类存在逻辑上的所属关系,一般只用在定义它的类或语句块里,实现没有通用意义的功能。外部引用时必须给出完整名称。 使用内部类的主要原因:可以访问外部…
泛型里如果不限制类型参数,它可以接受任意已定义的类型。很多时候我们只需要其中一部分,用户传入其他类型会在运行期出错。本节先限制类型参数的范围,再讲通配符 ?。 例如编写一个泛型方法,返回 Integer、Double 等数组中的最大值:元素得能取数值,就不能让 T 是任意类型。 写法 用在哪 含义 …
所谓泛型,就是“宽泛的数据类型”:不但值可以通过参数传递,类型也可以。它解决的是:既不想为每种类型写一遍重载,又不愿依赖不安全的向下转型。 Java 1.5 起引入泛型,参照 C++ 模板,本质是参数化类型(Parameterized Type)。类型参数只能表示引用类型;传入 int、double…
从功能上看,new 和 newInstance() 都能创建类的实例。前者是关键字,后者是方法。差别在于:newInstance() 走类加载机制,按运行时拿到的类名来反射创建;new 在源码里写死类型,直接创建。 为什么要两种方式?主要是软件的可伸缩、可扩展、可复用:明确知道要哪个类时用 new;…