类型和操作的分类
对于类型,不管是内置的还是用户定义的,都可以被分为可改变 和 不可变两种。
可改变的类型:StringBuilder,List,ArrayList、HashMap
不可改变的类型:String,基本类型及其封装对象类型,高精度数 BigInteger 和 BigDecimal,Collections.unmodifiableList
而抽象类型的操作符大致分类:
- 创建者creator:创建一个该类型的新对象。一个创建者可能会接受一个对象作为参数,但是这个对象的类型不能是它创建对象对应的类型。
- 生产者producer:通过接受同类型的对象创建新的对象。例如,
String
类里面的concat
方法就是一个生产者,它接受两个字符串然后据此产生一个新的字符串。 - 观察者observer:接受一个同类型的对象然后返回一个不同类型的对象/值。例如
List
的size
方法,它返回一个int
。 - 改造者mutator:改变对象的内容,例如
List
的add
方法,它会在列表中添加一个元素。
我们可以将这种区别用映射来表示:
- creator : t* → T
- producer : T+, t* → T
- observer : T+, t* → t
- mutator : T+, t* → void | t | T
其中T代表抽象类型本身;t代表其他的类型;+
代表这个参数可能出现一次或多次;*
代表这个参数可能出现零次或多次。例如, String.concat() 这个接受两个参数的生产者:
- concat : String × String → String
有些观察者不会接受其他类型的参数,例如:
- size : List → int
而有些则会接受很多参数:
- regionMatches : String × boolean × int × String × int × int → boolean
构造者通常都是用构造函数实现的,例如 new ArrayList() ,但是有的构造体是静态方法(类方法),例如 Arrays.asList()和 String.valueOf ,这样的静态方法也称为工厂方法。
改造者通常没有返回值(void
)。一个没有返回值的方法一定有副作用 ,因为不然这个方法就没有任何意义了。但是不是所有的改造者都没有返回值。例如Set.add() 会返回一个布尔值用来提示这个集合是否被改变了。在Java图形库接口中,Component.add() 会将它自己这个对象返回,因此add()
可以被连续链式调用。
抽象数据类型的例子
int 是Java中的原始整数类型,它是不可变类型,没有改造者。
- creators: 字面量
0
,1
,2
, … - producers: 算术符
+
,-
,*
,/
- observers: 比较符号
==
,!=
,<
,>
- mutators: 无
List 是Java中的列表类型,它是可更改类型。另外,List
也是一个接口,所以对于它的实现可以有很多类,例如 ArrayList
和 LinkedList
.
- creators:
ArrayList
和LinkedList
的构造函数, Collections.singletonList - producers: Collections.unmodifiableList
- observers:
size
,get
- mutators:
add
,remove
,addAll
, Collections.sort
String 是Java中的字符串类型,它是不可变类型。
- creators:
String
构造函数,valueOf
静态方法(工厂方法) - producers:
concat
,substring
,toUpperCase
- observers:
length
,charAt
- mutators: 无