`

Java中的容器讲解

    博客分类:
  • java
阅读更多

线性表,链表,集合,哈希表是常用的数据结构,在进行Java开发时,JDK已经为我们提供了一系列相应的类来实现基本的数据结构。这些类均在java.util包中。

Collection
├List
│-├LinkedList
│-├ArrayList
│-└Vector
│ └Stack
└Set

Map
├Hashtable
├HashMap
└WeakHashMap


主要分为两个分支:Collection和Map ,其中Map中存储的对象是以名值对的方式储存的,如:<name,value>

是字典的实现。

由Collection接口派生的两个接口是List和Set
其中,List的特点是:有顺序而可以重复Set的特点是:无顺序而不可重复
什么是重复?
不是说容器中有两个格子装了同一个对象,重复是指:a.equals(b) == true; 所以,当我们自定义对象作为容器的储存元素时,我们必须重写 java.lang.Object的equals方法,Object的默认equals只有当比较的参数是本身时才返回true,明显不是我们想要的,所以必须重写,而且,如果重写equals就必须重写hashCode()方法,因为,当我们的对象作为字典Map的键key时,我们的定位是同过 hashCode方法,这样来提高效率。注:两个对象equals若为TRUE,hashCode一定返回同样的int;但是,如果Equals返回 FALSE,hashCode不一定不同。


List接口

有重复、有序


List是有序的Collection,使用此接口能够精确的控制每个元素插入的位置。用户能够使用索引(元素在List中的位置,类似于数组下标)来访问List中的元素,这类似于Java的数组。

和下面要提到的Set不同,List允许有相同的元素。

除了具有Collection接口必备的iterator()方法外,List还提供一个listIterator()方法,返回一个 ListIterator接口,和标准的Iterator接口相比,ListIterator多了一些add()之类的方法,允许添加,删除,设定元素, 还能向前或向后遍历。

实现List接口的常用类有LinkedList,ArrayList,Vector和Stack。
ArrayList(数组表)- 有重复、有顺序。类似于Vector,都用于缩放数组维护集合。
区别:

1.同步性:Vector是线程安全的,也就是说是同步的,而ArrayList是线程序不安全的,不是同步的

2.数据增长:当需要增长时,Vector默认增长为原来一培,而ArrayList却是原来的一半

LinkedList(链表)-是双向链表,适合变更很多的List。

用在FIFO,用addList()加入元素 removeFirst()删除元素

用在FILO,用addFirst()/removeLast()

ListIterator提供双向遍历next() previous(),可删除、替换、增加元素


LinkedList类

LinkedList实现了List接口,允许null元素。此外LinkedList提供额外的get,remove,insert方法在 LinkedList的首部或尾部。这些操作使LinkedList可被用作堆栈(stack),队列(queue)或双向队列(deque)。

注意LinkedList没有同步方法。如果多个线程同时访问一个List,则必须自己实现访问同步。一种解决方法是在创建List时构造一个同步的List:
    List list = Collections.synchronizedList(new LinkedList(...));

ArrayList类
ArrayList实现了可变大小的数组。它允许所有元素,包括null。ArrayList没有同步。

size,isEmpty,get,set方法运行时间为常数。但是add方法开销为分摊的常数,添加n个元素需要O(n)的时间。其他的方法运行时间为线性。

每个ArrayList实例都有一个容量(Capacity),即用于存储元素的数组的大小。这个容量可随着不断添加新元素而自动增加,但是增长算法并 没有定义。当需要插入大量元素时,在插入前可以调用ensureCapacity方法来增加ArrayList的容量以提高插入效率。

和LinkedList一样,ArrayList也是非同步的(unsynchronized)。

一般情况下使用这两个就可以了,因为非同步,所以效率比较高。

Vector类
Vector非常类似ArrayList,但是Vector是同步的。由Vector创建的Iterator,虽然和ArrayList创建的 Iterator是同一接口,但是,因为Vector是同步的,当一个 Iterator被创建而且正在被使用,另一个线程改变了Vector的状态(例 如,添加或删除了一些元素),这时调用Iterator的方法时将抛出 ConcurrentModificationException,因此必须捕获该 异常。

Stack 类
Stack继承自Vector,实现一个后进先出的堆栈。Stack提供5个额外的方法使得Vector得以被当作堆栈使用。基本的push和pop方 法,还有 peek方法得到栈顶的元素,empty方法测试堆栈是否为空,search方法检测一个元素在堆栈中的位置。Stack刚创建后是空栈。

Set接口
Set的构造函数有一个约束条件,传入的Collection参数不能包含重复的元素。

Map接口
请注意,Map没有继承Collection接口,Map提供key到value的映射。一个Map中不能包含相同的key,每个key只能映射一个 value。Map接口提供3种集合的视图,Map的内容可以被当作一组key集合,一组value集合,或者一组key-value映射。

Map用于关键字/数值对,较高的存取性能。不允许重复的key,但允许重复的Value。

处理Map的三种集合

关键字集KeySet() 数值集value()   项目集enrySet()

四个具体版本

HashMap-散列表的通用映射表,无序,可在初始化时设定其大小,自动增长。

LinkedHashMap-扩展HashMap,对返回集合迭代时,维护插入顺序

WeakHashMap-基于弱引用散列表的映射表,如果不保持映射表外的关键字的引用,则内存回收程序会回收它

TreeMap-基于平衡树的映射表 



Hashtable类
Hashtable继承Map接口,实现一个key-value映射的哈希表。任何非空(non-null)的对象都可作为key或者value。
添加数据使用put(key, value),取出数据使用get(key),这两个基本操作的时间开销为常数。
Hashtable 通过initial capacity和load factor两个参数调整性能。通常缺省的load factor 0.75较好地实现了时间和空间的均衡。增大load factor可以节省空间但相应的查找时间将增大,这会影响像get和put这样的操作。
Hashtable是同步的。

HashMap类
HashMap和Hashtable类似,不同之处在于HashMap是非同步的,并且允许null,即null value和null key。,但是将HashMap视为Collection时(values()方法可返回 Collection),其迭代子操作时间开销和HashMap 的容量成比例。因此,如果迭代操作的性能相当重要的话,不要将HashMap的初始化容量设得过高,或者load factor过低。

WeakHashMap类
WeakHashMap是一种改进的HashMap,它对key实行“弱引用”,如果一个key不再被外部所引用,那么该key可以被GC回收。

一般情况下数据结构的选择:
多查少改选ArrayList
多改少查选LinkedList
如果大量数据进行检索选Map,


详细:
如果涉及到堆栈,队列等操作,应该考虑用List,对于需要快速插入,删除元素,应该使用LinkedList,如果需要快速随机访问元素,应该使用ArrayList。
如果程序在单线程环境中,或者访问仅仅在一个线程中进行,考虑非同步的类,其效率较高,如果多个线程可能同时操作一个类,应该使用同步的类。
要特别注意对哈希表的操作,作为key的对象要正确复写equals和hashCode方法。
尽量返回接口而非实际的类型,如返回List而非ArrayList,这样如果以后需要将ArrayList换成LinkedList时,客户端代码不用改变。这就是针对抽象编程。


同步性
Vector是同步的。这个类中的一些方法保证了Vector中的对象是线程安全的。而ArrayList则是异步的,因此ArrayList中的对象并不是线程安全的。因为同步的要求会影响执行的效率,所以如果你不需要线程安全的集合那么使用ArrayList是一个很好的选择,这样可以避免由于同步带来的不必要的性能开销。

数据增长

从内部实现机制来讲ArrayList和Vector都是使用数组(Array)来控制集合中的对象。当你向这两种类型中增加元素的时候,如果元素的数目超出了内部数组目前的长度它们都需要扩展内部数组的长度,Vector缺省情况下自动增长原来一倍的数组长度,ArrayList是原来的50%,所以最后你获得的这个集合所占的空间总是比你实际需要的要大。所以如果你要在集合中保存大量的数据那么使用Vector有一些优势,因为你可以通过设置集合的初始化大小来避免不必要的资源开销。

辅助类java.lang.Collections

这个类封装了一些List的算法,包括排序,逆向,随机排序等等。

重要需要实现的接口:

Comparable接口,当两个对象涉及比较操作时,使用这个接口的compareTo方法。

Iterator接口,涉及遍历时使用。

常见问题

1、Collection 和 Collections的区别。

Collections是个java.util下的类,它包含有各种有关java集合操作的静态方法。 

Collection是个java.util下的接口,它是各种java集合结构的父接口

2、List, Set, Map是否继承自Collection接口? List,Set是 Map不是

3、ArrayList和Vector的区别

(1).同步性:Vector是线程安全的,也就是说是同步的,而ArrayList是线程序不安全的,不是同步的

(2).数据增长:当需要增长时,Vector默认增长为原来一培,而ArrayList却是原来的一半

4、HashMap和Hashtable的区别

(1).历史原因:Hashtable是基于陈旧的Dictionary类的,HashMap是Java 1.2引进的Map接口的一个实现

(2).同步性:Hashtable是线程安全的,也就是说是同步的,而HashMap是线程序不安全的,不是同步的

(3).值:只有HashMap可以让你将空值作为一个表的条目的key或value



分享到:
评论

相关推荐

    JAVA容器讲解.pdf

    Java容器讲解PPT,Collection Map(HashMap TreeMap LinkedHashMap) List (ArrayList LinkedList Vector) Set (HashSet TreeSet LinkedHashSet)

    JAVA 容器用法详解

    JAVA 容器用法详解,关于JAVA容器的详细讲解

    spring boot基于Java的容器配置讲解

    在Spring Boot框架中,Java配置是一种常见的容器配置方式,它提供了更加灵活和可读性更强的配置模型,相比XML配置更加直观且易于维护。本文将深入探讨Spring Boot基于Java的容器配置,通过示例代码帮助理解其工作...

    JAVA核心技术讲解

    《JAVA核心技术讲解》 在Java编程领域,"JAVA核心技术讲解"是学习者和专业人士不可或缺的知识宝典。这里的“核心技术”通常涵盖了Java语言的基础、高级特性以及面向对象编程的核心概念。第八版,即(Core Java 8th ...

    Java知识的讲解(一些JAVA方面知识热点)

    TOMCAT是一款流行的Java Servlet容器,用于运行Web应用。它实现了Java EE的Servlet和JSP规范,使得开发者能够在服务器端处理HTTP请求。安装和配置Tomcat相对简单,开发者可以将打包好的WAR文件部署到Tomcat的webapps...

    JavaApplet实例讲解以及教程大全

    - **Applet容器**:Applet通常在HTML文档中嵌入,通过浏览器的Java插件运行。 - **Applet方法**:如`init()`, `start()`, `paint()`, `stop()`和`destroy()`,它们分别对应生命周期的不同阶段。 2. **JavaApplet...

    Java Servlet详细讲解

    在初始化阶段,Servlet可以通过ServletConfig对象获取容器中的配置信息,例如数据库连接设置。接着,Servlet进入处理请求的阶段,每个请求都会由ServletRequest对象接收,并通过ServletResponse对象进行响应。 ...

    java applet实例讲解

    本文将深入讲解Java Applet的概念、工作原理以及如何通过实例进行学习。 一、Java Applet概述 Java Applet是Java平台的一个组成部分,主要用于在网页中嵌入动态内容。它们由Java编写的类组成,这些类继承自`java....

    java高并发视频讲解

    本视频讲解旨在帮助开发者深入理解Java架构,并系统性地学习如何在Java环境中处理高并发问题。 首先,我们要理解高并发的基本概念。高并发是指在一定时间内,大量用户同时访问或操作同一系统、服务或资源,这要求...

    java基础方法讲解

    Java基础方法讲解主要涵盖方法的定义、调用、重载以及数组的相关操作。在Java中,方法是一段完成特定功能的代码块,可以被多次调用。方法的定义包括修饰符、返回值类型、方法名、参数类型和参数名。通常我们会使用`...

    java web开发讲解

    在Java Web开发中,我们经常使用的工具有Apache Tomcat服务器,这是一个开源的Servlet容器,能够运行Java Web应用。开发环境通常包括集成开发环境(IDE),如Eclipse或IntelliJ IDEA,它们提供了便捷的编码、调试和...

    台湾JAVA程序员经验讲解

    本文将基于“台湾JAVA程序员经验讲解”的主题,结合标签“java”,深入探讨一位台湾程序员的从业经历,以及他在Java编程中积累的知识和经验。 首先,台湾程序员在Java领域的成功往往离不开扎实的基础。他们通常会从...

    java课程详细讲解(针对初学者)

    在学习Java的过程中,动手实践是非常重要的,通过编写简单的程序来加深理解和记忆。随着经验的积累,可以逐渐学习更复杂的技术,如设计模式、框架(Spring、Hibernate等)以及并发编程等高级主题。记住,学习Java并...

    java NIO 详细讲解

    ### Java NIO 详细讲解 #### 一、引言与背景 随着计算机技术的发展和互联网应用的日益增多,数据处理的效率成为软件开发中的一个重要考量因素。Java NIO(New I/O)作为JDK 1.4引入的一项新技术,旨在解决传统IO...

    java学习书(代码讲解)

    "代码讲解"部分可能涵盖了如何创建和运行Java程序,以及如何在JSP中嵌入Java代码。这可能包括JSP的内置对象使用示例,如获取HTTP请求参数、设置响应头信息,以及如何使用session和cookie来管理用户会话。此外,可能...

    [课堂课件讲解]Java微服务实践-Spring Boot嵌入式Web容器.pptx

    Java微服务实践-Spring Boot嵌入式Web容器 Java微服务实践是指在微服务架构中使用Java语言开发微服务, Spring Boot...Java微服务实践中,Spring Boot嵌入式Web容器是非常重要的组件,可以帮助开发者快速开发微服务。

    java泛型实例讲解代码.rar

    通过阅读和理解`java泛型实例讲解代码`中的代码,你可以深入学习如何在实际编程中应用这些概念,以及它们如何提升代码的健壮性和可维护性。这个压缩包可能包含了各种示例,如泛型类、泛型方法、边界限制等,通过这些...

    java讲解ppt及实例代码

    这份“java讲解ppt及实例代码”资源将深入介绍Java的核心概念和技术,帮助学习者理解和掌握编程的基本技巧。以下是对其中可能包含的知识点的详细解读: 1. **Java基础知识**:这部分可能会涵盖Java的历史、特性以及...

    精通Java案例讲解

    在“精通Java案例讲解”这个主题中,我们将深入探讨Java编程语言在实际项目开发中的应用,特别是结合jsp(JavaServer Pages)技术进行Web应用程序的构建。这个教程旨在帮助你更全面、更深入地理解Java项目开发的过程...

Global site tag (gtag.js) - Google Analytics