《Java编程思想》 第十一章 持有对象

前言:

本系列是我本人阅读java编程思想这本书的读书笔记,主要阅读第五章到第十七章以及第二十一章的内容,今天的笔记是第十章

通常,程序总是根据运行时才知道的某些条件去创建新对象,在此之前,不会知道所需对象的数量,甚至不知道所需对象的类型,解决这个问题,需要在任意时刻任意位置创建任意数量的对象,所以就不能仅仅依靠创建命名的引用来持有每一个对象。有一种方法是使用数组来保存一组对象,但是使用数组是有局限性的,那就是数组是规定长度的,大多数情况下你在写程序的过程中并不知道需要多少个对象,这个时候就不能用数组了。

好在java提供了一组完整的容器类来解决这个问题,容器类也称为集合类,包括List,Map,Queue,Map,容器类提供了完善的方法来保存对象,更重要的是,这些容器类的实现都可以自动扩容,这样你就不用担心空间不足的问题了。

1. 泛型和类型安全的容器

java中有一个类叫做ArrayList,底层由数组实现,可以把它当成自动扩容的数组,但是,ArrayList有一个问题,那就是ArrayList存放的元素是Object类型,也就是说往ArrayList中添加元素的时候放什么类型都行,这种情况下会产生一个问题,那就是类型安全的问题,试想一下,比如第一次往ArrayList中存放的元素是A类型,而下一次存放的元素是B类型,那么遍历元素的时候,编译器会报出警告,提示没有使用泛型,而且取出的每个值都需要自己强制转换成想要的类型。有了泛型之后,问题就迎刃而解,声明一个ArrayList,加上一对尖括号<>,尖括号中放入类型参数,类型参数将指定容器所能保存的元素类型,遍历的时候也就不需要考虑强制类型转换的问题了,同样也就不存在类型安全的问题了。同时,指定了泛型的类型参数之后不仅能把确切的类型放到容器中,向上转型在这里也同样适用。

2. 容器的基本概念

  1. Collection 一个独立元素的序列,这些元素都符合一条或多条规则。List必须按照插入的顺序保存元素,Set不能保存重复值,Queue按照排队规则来确定对象产生的顺序。
  2. Map 键值对,允许使用键来查找值。

接下来书中开始讲述这些容器类的使用方法,这些都是API文档里有的方法,我在此就不再赘述了,主要讲一些这几个容器类的特点

List:有两种类型的List,一种就是普通的ArrayList,一种是LinkedList,普通的ArrayList因为底层实现是数组,所以随机访问速度很快,但是插入和删除元素的速度很慢,LinkedList底层是双向链表,还提供了优化的顺序访问,所以随机访问速度较慢,但是插入和删除速度很快。LinkedList还添加了可以作为栈,队列或双端队列的方法。

Set:Set不可以保存重复的元素,实际上,Set就是Collection,它和Collection的方法完全一样,而且Set中存放元素的顺序是随机的,Set中最常用到的方法就是contains,这个方法用来判断集合中是否含有指定的元素。还有一种Set,叫TreeSet,它是排过序的Set,TreeSet的底层实现是红黑树。

Map:将对象映射到其他对象是一种解决编程问题的杀手锏。而Map就可以用来把对象映射到其他对象。

Queue:队列是一个先进先出的容器,就是从容器的一端放入元素,从另一端取出元素,LinkedList实现了Queue接口,可以用来实现队列的功能。还有一种队列叫PriorityQueue,优先级队列,它声明下一个元素是最需要的元素。

3. 迭代器

任何容器类,都必须有某种方式可以插入元素并让他们再次取回,那么如果我要编写通用的代码,我只使用容器,不关心容器的类型,那么怎么样做才能不重写代码就应用于不同的容器中呢,答案是迭代器(也是一种设计模式)。迭代器是一个对象,它的作用是遍历并选择序列中的对象,而客户端程序员不必知道对象的类型,java中Iterator就是一种迭代器。这里要说明一下,常用的foreach语句块,就利用了Iterator接口的特点,只要创建了实现Iterable的类,都可以使用foreach语句块。

总结

《Java编程思想》 第十一章 持有对象

《Java编程思想》 第十一章 持有对象这张图是java集合类框架的整体结构图,本章就是讲述集合类框架的一些基本的概念,可以看到集合类框架其实一共只有四种容器,Map,List,Set,Queue,同时我们还了解到了这些容器类的一些基本的特点,这些容器类的一些子类还有一些特殊的用法和性能等,后面的章节会陆续讲到。到此,本章就结束了。