快速掌握Java中List和Set接口的基本使用

简介: 快速掌握Java中List和Set接口的基本使用

集合的概念


是一个工具类,作用为存储多个数据,通常用于替代数组


集合的特点


只能存放Object对象

只能存放引用类型

不能存放接口,只能存放接口实现类对象

来自java.util包

List接口


List的存储特点


有序、有下标、元素可以重复

常用实现类

ArrayList 最常用

JDK1.2 底层数组实现 查询快、增删慢 线程不安全,效率高

一般不用

JDK1.2 底层链表实现 增删快,查询慢 线程不安全,效率高

Vector 不用

JDK1.0 底层数组实现 都慢 线程安全,效率低

创建


通常使用多态


List 集合名=new 实现类名();


常用方法


集合名.方法名


boolean add(元素):将元素添加至集合末尾

void add(下标,元素):将元素添加至指定下标位置

boolean addAll(集合名):将指定集合所有元素添加至当前集合末尾

boolean addAll(下标,集合名):将指定集合所有元素添加至当前集合指定下标位置

void clear():清空集合元素

int size():获取集合长度

boolean contains(元素):判断集合中是否包含指定元素

boolean containsAll(集合名):判断集合中是否包含指定集合的所有元素

元素 get(下标):获取指定下标位置上的元素

int indexOf(元素):获取指定元素第一次出现的下标,不存在返回-1

int lastIndexOf(元素):获取指定元素最后一次出现的下标,不存在返回-1

boolean isEmpty():判断集合元素是否为空,不能判比null值

元素 remove(下标):移除指定下标的元素,返回该元素

元素 set(下标,新值):将指定下标位置的值替换为新值,返回旧值

void sort(比较器实现类对象):对集合元素按照指定规则排序

Object[] toArray():将集合转换为数组


代码示例


public class Test {
        public static void main(String[] args) {
            List list = new ArrayList();
            list.add(66);
            list.add(5);
            list.add(77);//66 5 77
            list.add(2,44);//66 5 44 77
            List list2 = new ArrayList();
            list2.add(2);
            list2.add(1);
            list.addAll(list2);//66 5 44 77 2 1
            list.addAll(1, list2);//66 2 1 5 44 77 2 1
            System.out.println("清空之前:"+list.size());
           // list.clear();
           // System.out.println("清空之后:"+list.size());
            System.out.println(list.contains(5));//t
            System.out.println(list.containsAll(list2));//t
            List list3 = new ArrayList();
            list3.add(66);
            list3.add(77);
            list3.add(88);
            System.out.println(list.containsAll(list3));//f
            System.out.println(list.get(3));//5
            System.out.println(list.indexOf(88));//-1
            System.out.println(list.lastIndexOf(2));//6
            //list.clear();
            System.out.println(list.isEmpty());
            List list4=null;
            //System.out.println(list4.isEmpty()); 空指针异常
            System.out.println(list.remove(3));//66 2 1 44 77 2 1
            // System.out.println(list.remove(2));
            list.set(1, 88);//66 88 1 44 77 2 1
            Object[] os=list.toArray();
            for(int i=0;i<os.length;i++){
                System.out.print(os[i]+" ");
            }
            System.out.println();
        }
    }


遍历方法


for+get()
 for (int i = 0; i < 集合名.size(); i++) {
       //i代表当前下标
       //通过集合名.get(i)的方式获取当前元素
   }
   如:
 for (int i = 0; i < list.size(); i++) {
        System.out.print(list.get(i)+" ");
         }
        System.out.println();


迭代器遍历

hasNext():判断是否存在下一元素
next():指针后移,获取下一元素
//获取迭代器对象
Iterator it=集合名.iterator();
while(it.hasNext()){//集合存在下一元素则继续后续操作
//通过it.next()使指针后移,得到元素
}
如:
Iterator it=list.iterator();
while(it.hasNext()){
System.out.print(it.next()+" ");
}
System.out.println();
tips:迭代过程中不允许对集合进行增删操作
外遍历forEach
for(数据类型 元素名(随便起) : 集合名){
//元素名就代表当前元素
}
如:
for (Object o: list) {
System.out.print(o+" ");
}
System.out.println();
本质也是迭代器遍历,内部不允许进行增删操作
JDK5.0
自遍历forEach
//匿名内部类
集合名.forEach(new Consumer() {
@Override
public void accept(Object o) {
//o就代表当前元素
}
});
 //lambda简化
         集合名.forEach(o-> {o就代表当前元素});
 如:
         list.forEach(new Consumer() {
             @Override
             public void accept(Object o) {
                 System.out.print(o + " ");
             }
         });
         System.out.println();
         // lambda
         list.forEach(o-> System.out.print(o+" "));


JDK8.0

泛型

作用


用于集合中,可以约束集合存储的数据类型


语法


List<数据类型> 集合名=new 实现类名<数据类型>();

1

使用


1. 如果集合中存放基本类型,则泛型必须声明为其包装类型

2. 声明泛型之后,集合中不允许存放其他类型的数据

3. 前后类型声明必须一致

4. 等号后边的泛型不声明,语法不规范

5. 等号前边的泛型不声明,泛型无意义


List<Integer> list = new ArrayList<Integer>();
        list.add(66);
        list.add(88);
       /* list.add("abc");
        list.add(5.5);*/
        list.forEach(new Consumer<Integer>() {
            @Override
            public void accept(Integer i) {
                System.out.println(i);
            }
        });


Set接口

Collection


是一个接口

是List和Set的父接口

所有集合都由Collection或Map派生

特点


存放着List和Set的共有方法

没有自己的直接实现类

Set的存储特点

无序、无下标、元素不可重复

常用实现类

HashSet

JDK1.2 底层哈希表实现(数组+链表 又名散列表) 线程不安全,效率高

LinkedHashSet

JDK1.2 是HashSet的子类,底层哈希表实现 线程不安全,效率高

TreeSet

JDK1.2 是SortedSet的实现类,底层红黑树实现 线程不安全,效率高

创建


利用多态


Set<泛型类型> 集合名 = new 实现类名<泛型类型>();


常用方法


全部继承自Collection

遍历方法

Iterator迭代器遍历

外遍历forEach

自遍历forEach

哈希表的去重过程


先通过调用元素的hashCode()方法得到哈希码值

然后通过哈希码值%数组长度得到存放下标

若该下标位置未存放元素,则直接存放

若已存有元素,则调用当前元素的equals()方法与其位置的所有元素进行值的比较

都不相同,则链表存放

若有相同,舍弃当前元素


注意事项

当集合中存放的为自定义类型时,必须重写hashCode和equals才能保证去重

LinkedHashSet能够保证元素存入和取出顺序一致

TreeSet可以实现对元素进行默认的升序排序

如果存放的为自定义类型,必须重写排序规则

两种排序方式:

实现Comparable接口,重写compareTo方法

要对谁排,就让谁实现

原理:让当前对象与参数对象进行比较

返回值规则:

从小到大:this的值>o的值,返回正数

从大到小:this的值>o的值,返回负数

相等返回0

实现Comparator接口,重写compare方法

在集合创建处的小括号内传入该接口的实现类对象


 

public class Test2 {
            public static void main(String[] args) {
                Set<Student> set = new TreeSet<Student>(new Comparator<Student>() {
                    @Override
                    public int compare(Student o1, Student o2) {
                        //根据学生年龄从大到小排序
                        return o2.getAge()-o1.getAge();
                    }
                });
                set.add(new Student("张三", 20));
                set.add(new Student("lisi", 21));
                set.add(new Student("lisi", 21));
                set.add(new Student("wangwu", 22));
                set.add(new Student("maliu", 19));
                set.forEach(s-> System.out.println(s));
            }
        }


默认识别第一种排序方式

第二种排序方式优先级高于第一种

List和set的区别

基本概念的区别

List 接口是一个有序的 Collection,使用此接口能够精确的控制每个元素插入的位置,能够通过索引(元素在List中位置,类似于数组的下标)来访问List中的元素,第一个元素的索引为 0,而且允许有相同的元素。List 接口存储一组不唯一,有序的对象。


Set 具有与 Collection 完全一样的接口,只是行为上不同,Set 不保存重复的元素。Set 接口存储一组唯一,无序的对象。


1.Set 接口实例存储的是无序的, 不重复的数据, List 接口实例存储的是有序的,可以重复的元素;

2.Set检索效率低下, 删除和插入效率高, 插入和删除不会引起元素位置改变

3.List和数组类似, 可以动态增长, 根据实际存储的数据的长度自动增长List的长度, 查找元素效率高, 插入删除效率低, 因为会引起其他元素位置改变 <实现类有ArrayList,LinkedList,Vector> ;

使用场景

List


常用的实现类有 ArrayList、LinkedList 和 Vector。ArrayList 最为流行,它提供了使用索引的随意访问,而 LinkedList 则对于经常需要从 List 中添加或删除元素的场合更为合适。

set


Set 接口最流行的几个实现类是 HashSet、LinkedHashSet 以及 TreeSet。最流行的是基于 HashMap 实现的 HashSet;TreeSet 还实现了 SortedSet 接口,因此 TreeSet 是一个根据其 compare() 和 compareTo() 的定义进行排序的有序容器。

相关文章
|
1天前
|
算法 Java 数据处理
从HashSet到TreeSet,Java集合框架中的Set接口及其实现类以其“不重复性”要求,彻底改变了处理唯一性数据的方式。
从HashSet到TreeSet,Java集合框架中的Set接口及其实现类以其“不重复性”要求,彻底改变了处理唯一性数据的方式。HashSet基于哈希表实现,提供高效的元素操作;TreeSet则通过红黑树实现元素的自然排序,适合需要有序访问的场景。本文通过示例代码详细介绍了两者的特性和应用场景。
13 6
|
1天前
|
存储 算法 Java
Java Set深度解析:为何它能成为“无重复”的代名词?
Java Set深度解析:为何它能成为“无重复”的代名词?本文详解Set接口及其主要实现类(HashSet、TreeSet、LinkedHashSet)的“无重复”特性,探讨其内部数据结构和算法实现,并通过示例代码展示最佳实践。
6 3
|
1天前
|
存储 Java 数据处理
Java Set接口凭借其独特的“不重复”特性,在集合框架中占据重要地位
【10月更文挑战第16天】Java Set接口凭借其独特的“不重复”特性,在集合框架中占据重要地位。本文通过快速去重和高效查找两个案例,展示了Set如何简化数据处理流程,提升代码效率。使用HashSet可轻松实现数据去重,而contains方法则提供了快速查找的功能,彰显了Set在处理大量数据时的优势。
6 2
|
1天前
|
Java 开发者
在Java集合世界中,Set以其独特的特性脱颖而出,专门应对重复元素
在Java集合世界中,Set以其独特的特性脱颖而出,专门应对重复元素。通过哈希表和红黑树两种模式,Set能够高效地识别并拒绝重复元素的入侵,确保集合的纯净。无论是HashSet还是TreeSet,都能在不同的场景下发挥出色的表现,成为开发者手中的利器。
10 2
|
1天前
|
Java
Java Set以其“不重复”的特性,为我们提供了一个高效、简洁的处理唯一性约束数据的方式。
【10月更文挑战第16天】在Java编程中,Set接口确保集合中没有重复元素,每个元素都是独一无二的。HashSet基于哈希表实现,提供高效的添加、删除和查找操作;TreeSet则基于红黑树实现,不仅去重还能自动排序。通过这两个实现类,我们可以轻松处理需要唯一性约束的数据,提升代码质量和效率。
9 2
|
1天前
|
Java
在Java的世界里,Set只接纳独一无二的元素。
【10月更文挑战第16天】在Java的世界里,Set只接纳独一无二的元素。本文通过拟人化的手法,讲述了重复元素从初次尝试加入Set被拒绝,到经历挣扎、反思,最终通过改变自己,成为独特个体并被Set接纳的全过程。示例代码展示了这一过程的技术实现。
8 1
|
Java
java中Set,Map,Stack一些简单用法
1 import java.util.Iterator; 2 import java.util.Stack; 3 import java.io.*; 4 import java.util.
631 0
|
4天前
|
安全 Java UED
Java中的多线程编程:从基础到实践
本文深入探讨了Java中的多线程编程,包括线程的创建、生命周期管理以及同步机制。通过实例展示了如何使用Thread类和Runnable接口来创建线程,讨论了线程安全问题及解决策略,如使用synchronized关键字和ReentrantLock类。文章还涵盖了线程间通信的方式,包括wait()、notify()和notifyAll()方法,以及如何避免死锁。此外,还介绍了高级并发工具如CountDownLatch和CyclicBarrier的使用方法。通过综合运用这些技术,可以有效提高多线程程序的性能和可靠性。
|
4天前
|
缓存 Java UED
Java中的多线程编程:从基础到实践
【10月更文挑战第13天】 Java作为一门跨平台的编程语言,其强大的多线程能力一直是其核心优势之一。本文将从最基础的概念讲起,逐步深入探讨Java多线程的实现方式及其应用场景,通过实例讲解帮助读者更好地理解和应用这一技术。
19 3