首页 科技正文

邯郸天气:java聚集详解

admin 科技 2020-05-01 43 0

1.java聚集是什么?

java聚集实际上是一种经常被运用到的java类库,其中提供了已经实现的的数据结构,省去了程序员再次编写数据结构的事情.在Leetcode中经常会被用到,有很主要的作用.

聚集系统

我们发现,无论是Set和List都是继续于Collection接口,实现Collection之中的方式,而他们又衍生出了HashSet,LinkedList等等我们经常使用的数据结构.

然则真相并不是云云的简朴.

对于Collection接口的实现,实在是由AbstractCollection类完成的.

此类提供了 Collection 接口的主干实现,从而最大限度地减少了实现此接口所需的事情。

Collection中需要实现的的方式:

 boolean add(E o) 确保此 collection 包罗指定的元素(可选操作)。 
 boolean addAll(Collection<? extends E> c) 
          将指定 collection 中的所有元素都添加到此 collection 中(可选操作)。 
 void clear() 
          移除此 collection 中的所有元素(可选操作)。 
 boolean contains(Object o) 
          若是此 collection 包罗指定的元素,则返回 true。 
 boolean containsAll(Collection<?> c) 
          若是此 collection 包罗指定 collection 中的所有元素,则返回 true。 
 boolean equals(Object o) 
          对照此 collection 与指定工具是否相等。 
 int hashCode() 
          返回此 collection 的哈希码值。 
 boolean isEmpty() 
          若是此 collection 不包罗元素,则返回 true。 
 Iterator<E> iterator() 
          返回在此 collection 的元素上举行迭代的迭代器。 
 boolean remove(Object o) 
          今后 collection 中移除指定元素的单个实例,若是存在的话(可选操作)。 
 boolean removeAll(Collection<?> c) 
          移除此 collection 中那些也包罗在指定 collection 中的所有元素(可选操作)。 
 boolean retainAll(Collection<?> c) 
          仅保留此 collection 中那些也包罗在指定 collection 的元素(可选操作)。 
 int size() 
          返回此 collection 中的元素数。 
 Object[] toArray() 
          返回包罗此 collection 中所有元素的数组。 
<T> T[] toArray(T[] a) 
          返回包罗此 collection 中所有元素的数组;返回数组的运行时类型与指定数组的运行时类型相同。 

AbstractCollection类实现的方式:


 boolean add(E o) 
          确保此 collection 包罗指定的元素(可选操作)。 
 boolean addAll(Collection<? extends E> c) 
          将指定 collection 中的所有元素添加到此 collection 中(可选操作)。 
 void clear() 
          今后 collection 中移除所有元素(可选操作)。 
 boolean contains(Object o) 
          若是此 collection 包罗指定的元素,则返回 true。 
 boolean containsAll(Collection<?> c) 
          若是此 collection 包罗指定 collection 中的所有元素,则返回 true。 
 boolean isEmpty() 
          若是此 collection 不包罗元素,则返回 true。 
abstract  Iterator<E> iterator() 
          返回在此 collection 中的元素上举行迭代的迭代器。 
 boolean remove(Object o) 
          今后 collection 中移除指定元素的单个实例(若是存在)(可选操作)。 
 boolean removeAll(Collection<?> c) 
          今后 collection 中移除包罗在指定 collection 中的所有元素(可选操作)。 
 boolean retainAll(Collection<?> c) 
          仅在此 collection 中保留指定 collection 中所包罗的元素(可选操作)。 
abstract  int size() 
          返回此 collection 中的元素数。 
 Object[] toArray() 
          返回包罗此 collection 中所有元素的数组。 
<T> T[] toArray(T[] a) 
          返回包罗此 collection 中所有元素的数组;返回数组的运行时类型是指定数组的类型。 
 String toString() 
          返 

出了一个hashcode方式,AbstractCollection类实现了险些所有的功效.

AbstractCollection类又有三个差别的子类AbstractList, AbstractQueue, AbstractSet.我们从名字就可以知道,这就是三种差别的数据结构.于是这样基本就可以分析出来.

聚集类的构建框架如下.

所有的聚集都是依赖这种方式构建的,用一个抽象类实现接口,然后再用聚集类去实现这些抽象类,来完成构建聚集的目的.

这是完整的构建图.

这实在是为了人人有一个头脑,就是在Collection实现的方式,在继续实现他的各个聚集中也都市实现.

如下是本文的目录:

(一) Iterator接口--迭代器

{
   
 boolean hasNext()  若是仍有元素可以迭代,则返回 true。 
 E next()    返回迭代的下一个元素。 
 void remove()  删除
     default void forEach 实现了迭代器接口的类才可以使用forEach
}
 

    

这几个方式有着很主要的意义:

  1. 所有实现Collection接口(也就是大部分聚集)都可以使用forEach功效.

  2. 通过频频挪用next()方式可以接见聚集内的每一个元素.

  3. java迭代器查找的唯一操作就是依赖挪用next,而在执行查找义务的同时,迭代器的位置也在改变.

  4. Iterator迭代器remove方式会删除上次挪用next方式返回的元素.这也意味之remove方式和next有着很强的依赖性.若是在挪用remove之前没有挪用next是不合法的.

    这个接口衍生出了,java聚集的迭代器.

    java聚集的迭代器使用

下面是迭代器的一个小栗子:

class test {
    public static void run() {
        List<Integer> list = new LinkedList<>();
        list.add(1);
        list.add(2);
        list.add(3);
        list.add(3);
        Iterator<Integer> iterator = list.iterator();//依赖这个方式天生一个java聚集迭代器<--在Colletion接口中的方式,被所有聚集实现.
//        iterator.remove();报错java.lang.IllegalStateException
        iterator.next();
        iterator.remove();//不报错,删掉了1
        System.out.println(list);//AbstractCollection类中实现的toString让list可以直接被打印出来
        while (iterator.hasNext()) {//迭代器,hasNext()聚集是否为空
            Integer a = iterator.next();//可以用next接见每一个元素
            System.out.println(a);//2,3 ,3
        }
        for (int a : list) {//也可以使用foreach
            System.out.println(a);//2,3,3
        }
    }
    public static void main(String[] args) {
        run();
    }
}

固然你也会有点好奇,为什么remove方式前面必须随着一个next方式.实在这个只能这么注释.

迭代器的next方式的运行方式并不是类似于数组的运行方式.

固然,这张图主要是让你明白一下.

数组的指针指向要操作的元素上面,而迭代器却是将要操作的元素放在运动轨迹中心.

本质来讲,迭代器的指针并不是指在元素上,而是指在元素和元素中心.

假设现在挪用remove().被删除的就是2号元素.(被迭代器谁人圆弧笼盖在其中的谁人元素).若是再次挪用,就会报错,由于圆弧之中的2号元素已经消逝,那里是空的,无法删除.

(二) Collection接口

这个工具是一个被LIst,Set,Queue的超类, 这个接口中的方式,构成了聚集中主要的方式和内容.剩下的聚集往往都是对这个接口的扩充.

方式如下:

boolean add(E o) 
          确保此 collection 包罗指定的元素(可选操作)。 
 boolean addAll(Collection<? extends E> c) 
          将指定 collection 中的所有元素添加到此 collection 中(可选操作)。 
 void clear() 
          今后 collection 中移除所有元素(可选操作)。 
 boolean contains(Object o) 
          若是此 collection 包罗指定的元素,则返回 true。 
 boolean containsAll(Collection<?> c) 
          若是此 collection 包罗指定 collection 中的所有元素,则返回 true。 
 boolean isEmpty() 
          若是此 collection 不包罗元素,则返回 true。 
abstract  Iterator<E> iterator() 
          返回在此 collection 中的元素上举行迭代的迭代器。 
 boolean remove(Object o) 
          今后 collection 中移除指定元素的单个实例(若是存在)(可选操作)。 
 boolean removeAll(Collection<?> c) 
          今后 collection 中移除包罗在指定 collection 中的所有元素(可选操作)。 
 boolean retainAll(Collection<?> c) 
          仅在此 collection 中保留指定 collection 中所包罗的元素(可选操作)。 
abstract  int size() 
          返回此 collection 中的元素数。 
 Object[] toArray() 
          返回包罗此 collection 中所有元素的数组。 
<T> T[] toArray(T[] a) 
          返回包罗此 collection 中所有元素的数组;返回数组的运行时类型是指定数组的类型。 
 String toString() <--很主要
          返 

实在我们并不一定要把这些方式都记着

我们只要记着Collection工具实现了这些种类的方式就可以了(可以现查API,不是..

然则确实,这些方式记着了有很大的用处.

添加元素(两种) 添加一个元素,添加一个聚集
删除元素(三种)  删除一个元素,删出一个聚集,只保留一个聚集
判断巨细
酿成数组
是否为空
清空

java聚集的泛型使用

到这里我们还要解说一个问题,就是除了Map的聚集类型(看看上面的继续表,map是单独一个分支)都可以传入Collection为参数的函数内里去.

public class Test {
    public static void  display(Collection<?> a){
        System.out.println(a);
    }

    public static void main(String[] args) {
        List<Integer> list=new LinkedList<>();//链表
        list.add(1);
        list.add(2);
        list.add(4);
        list.add(3);
        display(list);//[1, 2, 4, 3]
        Set<Integer> set=new TreeSet<>();//树集
        set.addAll(list);
        //在这里之以是两者输出差别,是由于树集有着一个自动排序的功效.其缘故原由在于对于treeset内部结构的实现和LinkedList有所差别
        display(set);//[1, 2, 3, 4]
        
    }
}

java聚集中使用泛型的利益

为什么在java聚集中经常使用泛型.除了为了防止输入错误的数据,更主要的是若是用了泛型也会让操作加倍的利便,省去了强制转化的历程.

以下两个是准备

public class AppleAndOrangeWithOutGenerics {
    @SuppressWarnings("unchecked")//这个只能抑制忠告信息,用它就不会有忠告

    public static void main(String args[]) {
        /**
         * 不用泛型
         */
//        ArrayList apples=new ArrayList();
//        for (int i = 0; i <3 ; i++) {
//            apples.add(new Apple());
        //在ArrayList无论放进去之前是什么,再放进去之后都市酿成Object类型,
//            apples.add(new Orange());
        //会报一个小小的warning,由于没有使用泛型.<-只有删掉这个句子执行才不报错
//        }
//            for (int j = 0; j <apples.size() ; j++) {
//                System.out.println(((Apple)apples.get(j)).id());
        //若是没有泛型的阻挡,输入Orange类型基本不会被发现.异常的危险
//            }

        /**
         * 使用泛型
         */
        ArrayList<Apple> apples = new ArrayList();
        for (int i = 0; i < 3; i++) {
            apples.add(new Apple());
//            apples.add(new Orange());//在这里直接就报错了,让这种错误在编译期就被发现

        }
        for (int j = 0; j < apples.size(); j++) {
            //用了反省之后连强制转换都不需要了
            System.out.println(( apples.get(j)).id());//若是没有泛型的阻挡,输入Orange类型基本不会被发现.异常的危险
        }
    }
}

以是使用泛型有很大的利益.

(三) List

List是一个有序聚集,元素会增添到容器中特定的位置,可以接纳两种方式接见元素:使用迭代器接见或者使用一个整数索引接见.后一种方式称为随机接见.

为此List接口多界说了一些方式,来实现这一点

void add(int index,E element);//这个和上面差别,带了index.
void remove(int index);
E get(int index);
E set(int index,E element);

我们知道实现LIST接口的类中有一个类叫做AbstractList,他的两个子类分别是LinkedList和ArrayList这两种.那么问题是链表可不可以使用这个add方式.

谜底是可以的.实际上链表使用随机接见,只不过是慢了点而已.若是有可能,照样使用迭代器为好.

LIST主要有两种类.一个是LinkedList一个是ArrayList.

LinkedList

我们就从一个程序看一看LinkedList到底怎么用.

/**
 * LinkedLIST也像ArrayList一扬实现了基本的List接口,然则他执行一些操作效率更高,好比插入.
 * LIST为空就会抛出NoSuchElement-Exception
 * Created by 22643 on 2020/4/17.
 */
public class LinkedListFeatures {
    public static void main(String[] args) {
        LinkedList<Pet> pets=new LinkedList<Pet>(Pets.arrayList(5));//后面括号中的意思是天生五个Pets工具
        System.out.println("pets = [" + pets + "]");
        System.out.println("pets.getFirst() "+pets.getFirst());//取第一个
        System.out.println("pets.element "+pets.element());//也是取第一个,跟first完全相同.
        //若是列表为空如上两个内容返回NoSuchElement-Exception
        System.out.println("pets.peek()"+pets.peek());//peek跟上面两个一扬,只是在列表为空的时刻返回null
        System.out.println(pets.removeFirst());
        System.out.println(pets.remove());//这两个完全一样,都是移除并返回列表头,列表空的时刻返回NoSuchElement-Exception
        System.out.println(pets.poll());//稍有差异,列表为空的时刻返回null
        pets.addFirst(new Rat());//addFirst将一个元素插入头部,addLast是插到尾部
        System.out.println(pets);
        pets.add(new Rat());//将一个元素插入尾部
        System.out.println(pets);
        pets.offer(new Rat());//与上面一扬,将一个元素插入尾部
        System.out.println(pets);
        pets.set(2,new Rat());//将替换为指定的元素
        System.out.println(pets);
    }

}

实际上LinkedList有异常多的方式,由于LinkedList是被用来实现多中数据结构的.不只可以实现行列,甚至另有可以实现栈的相关方式.

我们对此举行分类:

栈相关的操作方式:

 E poll() 
          找到并移除此列表的头(第一个元素)。 
 peek() 
          找到但不移除此列表的头(第一个元素)。
 void addFirst(E o) 加入开头可以看成add用
             

行列操作方式:(LinkedList实现了Queue的接口,以是说可以操作用来构建行列)

注重行列是FIFO(先进先出)行列,以是凭据实现,从通俗行列是从行列的尾部插入,从头部移除,.

以是方式如下:

E element() 首元素
boolean offer(E o)将指定行列插入桶
E peek() 检索,然则不移除行列的头
E pool()检索并移除此行列的头,为空返回null.
E remove()检索并移除此行列的头

一样平常来讲聚集中的方式在移除方式都市有一个为空的时刻返回null的方式,和一个为空的时刻返回null的方式.类似于pool()和remove()

我们一会到Queue的时刻还会将这些再将一次.

ArrayList

我们也从一个程序来看这个

public class ListFeatures {
    public static void main(String[] args) {
        Random rand=new Random(47);//相同的种子会发生相同的随机序列。
        List<String> list=new ArrayList<>();
        list.add("demo3");
        list.add("demo2");
        list.add("demo1");//加入方式
        System.out.println("插入元素前list聚集"+list);//可以直接输出
        /**
         * /void add(int index, E element)在指定位置插入元素,后面的元素都往后移一个元素
         */
        list.add(2,"demo5");
        System.out.println("插入元素前list聚集"+list);
        List<String> listtotal=new ArrayList<>();
        List<String> list1=new ArrayList<>();
        List<String> list2=new ArrayList<>();
        list1.add("newdemo1");
        list1.add("newdemo2");
        list1.add("newdemo2");
        /**
         * boolean addAll(int index, Collection<? extends E> c)
         * 在指定的位置中插入c聚集所有的元素,若是聚集发生改变,则返回true,否则返回false。
         * 意思就是当插入的聚集c没有元素,那么就返回false,若是聚集c有元素,插入乐成,那么就返回true。
         */
        boolean b=listtotal.addAll(list1);
        boolean c=listtotal.addAll(2,list2);
        System.out.println(b);
        System.out.println(c);//插入2号位置,list2是空的
        System.out.println(list1);
        /**
         * E get(int index)
         * 返回list聚集中指定索引位置的元素
         */
        System.out.println(list1.get(1));//list的下标是从0最先的
        /**
         * int indexOf(Object o)
         * 返回list聚集中第一次泛起o工具的索引位置,若是list聚集中没有o工具,那么就返回-1
         */
        System.out.println(list1.indexOf("demo"));
        System.out.println(list1.indexOf("newdemo2"));
//若是在list中有相同的数,也没有问题.
        //然则若是是工具,由于每个工具都是举世无双的.以是说若是传入一个新的工具,indexof和remove都是无法完成义务的
        //要是删除,可以先找到其位置,然后在举行删除.
        //Pet p=pets.get(2);
        //pets.remove(p);
        /**
         * 查看contains查看参数是否在list中
         */
        System.out.println(list1.contains("newdemo2"));//true
        /**
         * remove移除一个工具
         * 返回true和false
         */
        //只删除其中的一个
        System.out.println(list1.remove("newdemo2"));//[newdemo1, newdemo2]
        System.out.println(list1);
        List<String> pets=list1.subList(0,1);//让你从较大的一个list中建立一个片断
        //containall一个list在不在另一个list中
        System.out.println(pets+"在list中嘛"+list1.containsAll(pets));//[newdemo1]在list中嘛true
        //由于sublist的背后就是初始化列表,以是对于sublist的修改会直接反映到原数组上面
        pets.add("new add demo");
        System.out.println(list1);//[newdemo1, new add demo, newdemo2]
        Collections.sort(pets);
        System.out.println(
                pets
        );//new add demo, newdemo1
        System.out.println(list1.containsAll(pets));//true-----变换位置不会影响是否在list1中被找到.
        list1.removeAll(pets);//移除在参数list中的所有数据
        /**
         * list1[newdemo1, new add demo, newdemo2]
         * pets[new add demo, newdemo1]
         */
        System.out.println(list1);//[newdemo2]
        System.out.println(list1.isEmpty());//是否为空
        System.out.println(list1.toArray());//将list变为数组
        //list的addAll方式有一个重载的.可以让他在中心加入

    }
}

这个对照适合非顺序存储.

(四)(五)Set

Set实际上也是一种映射关系的聚集和Map对照像.然则它实现的依然是Collection的接口.

而且Set中的方式和Collection的方式险些完全一样.

唯一的区别在于add方式不允许增添重复的元素.在挪用equal时,若是两个Set中的元素都相等,无论两者的顺序若何,这两个Set都市相等.

set的特征

Set不保留重复的元素.
Set就是Collection,只是行为差别.
HashSet使用了散列,它打印的时刻,输出的元素不会正常排列
TreeSet使用了储存在红黑树结构中,,以是输出的元素会正常排列

固然Set最主要的事情就是判断存在性,目的是看一个元素到底存不存在这个聚集之中.

下面放上两个Set的例子:

SortedSet(TreeSet)

public class SortedSetOfInteger {
    public static void main(String[] args) {
        Random random=new Random(47);
        SortedSet<Integer> intset=new TreeSet<>();
        for (int i = 0; i <100 ; i++) {
            intset.add(random.nextInt(30));
        }
        System.out.println(intset);//set特征只能输入相同的数,别看输入了100个数,然则实际上只有30个进去了.
        //这个有序了.这就是treeset的劳绩,由于内部的实现时红黑树,以是来说.这就简朴了一些
    }
}

HashSet

public class SetOfInteger {
    public static void main(String[] args) {
        Random rand=new Random(47);
        Set<Integer> intset=new HashSet<>();//建立一个HashSet
        for (int i = 0; i <100 ; i++) {
            intset.add(rand.nextInt(30));
        }
        System.out.println(intset);//set特征只能输入相同的数,别看输入了100个数,然则实际上只有30个进去了.
    }
}

这里要讲一下HashSet。HashSet不在意元素的顺序,凭据属性可以快速的接见所需要的工具。散列表为每个工具盘算一个整数,成为散列码...散列码是实例发生的一个整数。

散列表(HashSet)散列表用链表数组实现。每个列表称为通。想要查找表中工具的位置就盘算它的散列码。然后与通的总数取余,获得的数就是保留这个元素的通的索引。

然则桶总有被沾满的一刻。

为了应对这种情形,需要用新工具与桶中所有工具对照,看是否存在。

为了控制性能就要能界说初始桶数,设置为要插入元素的75%-150%,最好为素数。

这个时刻就要执行再散列,让这个散列表获得更多的内容。

再散列:

需要建立一个桶数更多的表,并将所有元素插入这个新表中。装填因子绝对什么时刻在执行,若是装填因子为0.75那么就是在表中75%的位置被沾满时,表会给如双倍的桶数自动散列。

Queue

行列是数据结构中对照主要的一种类型,它支持 FIFO,尾部添加、头部删除(先进行列的元素先出行列),跟我们生涯中的排队类似。

然则在聚集中的Queue并没有单独的实现类,而是用LinkedList实现的。实在你只要看一眼LinkedList的方式就知道,他完全可以实现行列的操作。

add()尾部添加
removeFirst()删除头部元素
peek()查看头部元素

Queue主要有两种差别的类型.

分别是优先级行列和Deque行列

PriorityQueue

优先级行列中元素可以凭据随便的顺序插入,却凭据目的排序的顺序举行检索,也就是无论什么时刻挪用remove移除的都是当前最小的元素。

优先级使用了一种堆,一个可以自我调节的二叉树,对树举行执行添加和删除。它可以让最小的元素移动到跟,而不必花时间对其排序。

固然,你也可以自己对其举行排序.

小栗子:

import java.text.DecimalFormat;
import java.util.Comparator;
import java.util.PriorityQueue;
import java.util.Queue;

/**
 * @Author:sks
 * @Description:
 * @Date:Created in 10:39 2018/1/11
 * @Modified by:
 **/

//二维平面上一个点
 class point {
    //坐标x
    double x;

    //坐标y
    double y;
    public point(double x, double y){
        this.x = x;
        this.y = y;
    }
}
//排序函数
class PointComparator {
    private   point pointOne;
    private point pointTwo;
    public double distance;
    public PointComparator(point pointOne,point pointTwo)
    {
        this.pointOne = pointOne;
        this.pointTwo = pointTwo;
        computeDistance();
    }
    //盘算两点之间距离
    private void computeDistance() {
        double val = Math.pow((this.pointOne.x - this.pointTwo.x),2) +
                Math.pow((this.pointOne.y - this.pointTwo.y),2);
        this.distance = Math.sqrt(val);
    }


}
public class PriorityQueuep_test {

    public static void main(String args[]){
         Comparator<PointComparator> OrderDistance =  new Comparator<PointComparator>(){
            public int compare(PointComparator one, PointComparator two) {
                if (one.distance < two.distance)
                    return 1;
                else if (one.distance > two.distance)
                    return -1;
                else
                    return 0;
            }
        };

        //界说一个优先行列,用来排序随便两点之间的距离,从大到小排
        Queue<PointComparator> FsQueue = new PriorityQueue<PointComparator>(10,OrderDistance);

        for (int i=0;i<6;i++){

            java.util.Random r= new java.util.Random(10);
            point one =new point(i*2+1,i*3+2);
            point two =new point(i*5+2,i*6+3);
            PointComparator nodecomp = new PointComparator(one,two);

            DecimalFormat df = new DecimalFormat("#.##");
            FsQueue.add(nodecomp);
        }
        DecimalFormat df = new DecimalFormat("#.###");
        for (int i = 0;i<6;i++){
            System.out.println(df.format(FsQueue.poll().distance));
        }
    }

}

Deque

deque也有些庞大,它可以用ArrayDeque实现,也可以用LinkedList实现.

线性聚集,支持两头的元素插入和移除。Deque是double ended queue的简称,习惯上称之为双端行列。大多数Deque 实现对它们可能包罗的元素的数目没有牢固的限制,然则该接口支持容量限制的deques以及没有牢固巨细限制的deque。

作者:我是吸血鬼
链接:https://www.jianshu.com/p/d78a7c982edb
泉源:简书
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

由于自己也是LinkedList实现的,以是其自己的方式和LinkedList差不了若干.

小栗子:

public class Main {
    public static void main(String[] args) {
        Deque<String> deque = new LinkedList<>();
        deque.offerLast("A"); // A
        deque.offerLast("B"); // B -> A
        deque.offerFirst("C"); // B -> A -> C
        System.out.println(deque.pollFirst()); // C, 剩下B -> A
        System.out.println(deque.pollLast()); // B
        System.out.println(deque.pollFirst()); // A
        System.out.println(deque.pollFirst()); // null
    }
}

Stack

stack的名字人人都知道,就是栈.一个先进后出的数据结构,这里我并不认为应该使用java聚集中提供的栈聚集.

而是应该使用LinkedList来构建聚集:
一个小义务:

用LinkedList实现栈

public class Stack<T> {
    private LinkedList<T> storage=new LinkedList<>();//用LinkedList作为栈的焦点
    public void push(T v){ storage.addFirst(v);}//
    public T peek(){ return storage.getFirst();}
    public T pop(){return storage.removeFirst();}
    public boolean empty(){return storage.isEmpty();}
    public String toString(){return storage.toString();}
}

这样做有一个利益,就是这样的栈可以有更多种的方式,可以接纳更多种的方式.无疑这样的栈会更好一些.

以是我推荐人人用栈的时刻,用LinkedList来实现.

MAP

讲了Collection接口实现的种种聚集,我们就要讲讲非Collection的聚集.这意味着你在Collection中记着的方式在这个内里完全用不到了.

我们知道一些键的信息,想要知道与之对应的元素.映射结构就是为此设计的,映射用来存放键值对,如提供了键就能查到值.

和Set一样,HashMap要比TreeMap要快上一些,然则TreeMap有序.这与Set很相似,究竟Set实在也是映射结构.

每当往映射加入工具是,必须同时提供一个键.

键是唯一的,不能对同一个键放两个值.若是对同一个键挪用两次put方式,第二次挪用会取代第一个.

要想处置所有的键和值,那就应该使用foreach

列子如下:

public class MapOfList {
    public static Map<Person, List<? extends Pet>> people=new HashMap<>();
    static {
        people.put(new Person("dawn"), Arrays.asList(new Cymric("Molly"),new Mutt("Spot")));
        //就写一个了,有点懒了.
    }
    public static void main(String[] args) {
        System.out.println(people.keySet());//返回的是键组成的set
        System.out.println(people.values());//返回的时值组成的set
        for (Person person:people.keySet()
             ) {
            System.out.println(person+"has :");
            for (Pet pet:people.get(person)
                 ) {
                System.out.println(pet);

            }
        }
    }
}

下面另有一个HashMap使用的例子

public class PetMap {
    public static void main(String[] args) {
        Map<String, Pet> petMap=new HashMap<String, Pet>();
        petMap.put("My Cat",new Cat("MALL"));
        petMap.put("My Dog",new Dog("DOGGY"));
        petMap.put("My Haster",new Hamster("Bosco"));
        System.out.println(petMap);
        Pet dog=petMap.get("My Dog");
        System.out.println(dog);
        System.out.println(petMap.containsKey("My Dog"));//
        System.out.println(petMap.containsValue(dog));//
    }
}

,

sunbet 申博

sunbet 申博www.sunbet88.us是Sunbet指定的Sunbet官网,Sunbet提供Sunbet(Sunbet)、Sunbet、申博代理合作等业务。

版权声明

本文仅代表作者观点,
不代表本站Sunbet的立场。
本文系作者授权发表,未经许可,不得转载。

评论