Java进阶_集合
集合
一、集合的概念
1、什么是集合
- 概念:对象的容器,定义了对多个对象进行操作的常用方法。可实现数组的功能。
- 和数组区别:
- (1)数组长度固定,集合长度不固定
- (2)数组可以存储基本类型和引用类型,集合只能引用类型
- 位置: java. util. *;
2、Collection体系集合
3、Collection父接口
Collection接口
- 特点:代表一组任意类型的对象,无序、无下标、不能重复。、
- 方法:
- boolean add(0bject obj) //添加一个对象。
- boolean addAll (Collection c) //将 一个集合中的所有对象添加到此集合中。
- void clear() //清空此集合中的所有对象。
- boolean contains (Object o) //检查此集合中是否包含o对象
- boolean equals (0bject o) //比较此集合是否与指定对象相等。
- boolean isEmpty() //判断此集合是否为空
- boolean remove (Object o) //在 此集合中移除o对象
- int size() //返回此集合中的元素个数。
- 0bject[] toArray() //将此集合转换成数组。
二、Collection接口
Collection的使用一:
package com.mike.test;
/*
collection接口的使用
(1)添加元素
(2)删除元素
(3)遍历元素
(4)判断
*/
import java.util.ArrayList;
import java.util.Collection;
import java.util.Iterator;
public class Test {
public static void main(String[] args){
//创建集合
//ArrayList 有序,有下标,可重复
Collection collection = new ArrayList();
// (1)添加元素
collection.add("苹果");
collection.add("西瓜");
collection.add("香蕉");
collection.add("青枣");
collection.add("鸭梨");
collection.add("火龙果");
System.out.println("元素个数:"+collection.size());
System.out.println(collection);
// (2)删除元素
collection.remove("鸭梨");
System.out.println("-------------------------------");
System.out.println("元素个数:"+collection.size());
System.out.println(collection);
// (3)遍历元素【重点】
//3.1、使用增强的for(好处是不需要知道下标)
System.out.println("-----第一种遍历方式,增强for-----");
for (Object object : collection) {
System.out.println(object);
}
//3.2、使用迭代器(迭代器是专门用来遍历集合的一种方式)
//迭代过程不能使用集合的删除方法,否则会出现并发修改异常
System.out.println("-----第二种遍历方式,使用迭代器-----");
//hasNext();有没有下一个元素,
//next();获取下一个元素
//remove();删除当前元素
Iterator it = collection.iterator();
while (it.hasNext()){
String s = (String) it.next();
System.out.println(s);
}
// (4)判断
System.out.println("----------------------------");
System.out.println("是否有西瓜:"+collection.contains("西瓜"));
System.out.println("集合是否为空:"+collection.isEmpty());
}
}
/*输出结果
元素个数:6
[苹果, 西瓜, 香蕉, 青枣, 鸭梨, 火龙果]
-------------------------------
元素个数:5
[苹果, 西瓜, 香蕉, 青枣, 火龙果]
-----第一种遍历方式,增强for-----
苹果
西瓜
香蕉
青枣
火龙果
-----第二种遍历方式,使用迭代器-----
苹果
西瓜
香蕉
青枣
火龙果
----------------------------
是否有西瓜:true
集合是否为空:false
*/
Collection的使用二:
集合存对象
Student类
package com.mike.test;
public class Student {
private String name;
private int age;
public Student() {
}
public Student(String name, int age) {
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
@Override
public String toString() {
return "Student{" + "name=" + name + ", age=" + age + '}';
}
@Override
public boolean equals(Object obj) {
//1.是不是同一个对象
if (this==obj){
return true;
}
//2.是不是为空
if (obj==null){
return false;
}
//3.判断是否是Student类型
if (obj instanceof Student){
Student s =(Student) obj;
//4.比较属性
if (this.name.equals(s.getName())&&this.age==s.getAge()){
return true;
}
}
//5.不满足条件,返回false
return false;
}
}
Test类
package com.mike.test;
/*
collection的使用:保存学生信息
(1)添加元素
(2)删除元素
(3)遍历元素
(4)判断
*/
import java.util.ArrayList;
import java.util.Collection;
import java.util.Iterator;
public class Test {
public static void main(String[] args){
//新建Collection对象
Collection collection = new ArrayList();
Student student1 = new Student("唐僧", 19);
Student student2 = new Student("孙悟空", 20);
Student student3 = new Student("猪八戒", 20);
Student student4 = new Student("沙僧", 27);
Student student5 = new Student("白龙马", 21);
//1、添加学生信息
collection.add(student1);
collection.add(student2);
collection.add(student3);
collection.add(student4);
collection.add(student5);
System.out.println("元素个数"+collection.size());
System.out.println(collection.toString());
//2、删除(这里的删除不是删除学生对象,而是删除学生对象在集合中的地址,new的学生对象还在堆当中)
collection.remove(student1);
//collection.clear();//清除集合中的元素
System.out.println("------------------------------");
System.out.println("删除之后");
System.out.println("元素个数"+collection.size());
System.out.println(collection.toString());
//3、遍历3.1、增强for
System.out.println("------------------------------");
System.out.println("遍历元素增强for");
for (Object object : collection) {
Student s = (Student) object;
System.out.println(s.toString());
}
//3、遍历3.2、迭代器
System.out.println("------------------------------");
System.out.println("遍历元素迭代器");
Iterator it = collection.iterator();
while (it.hasNext()){
Student s = (Student) it.next();
System.out.println(s.toString());
}
//4、判断
System.out.println("------------------------------");
System.out.println("判断元素是否存在");
System.out.println("student1是否存在:"+collection.contains(student1));
System.out.println("student2是否存在:"+collection.contains(student2));
}
}
/*输出结果
元素个数5
[Student{name=唐僧, age=19}, Student{name=孙悟空, age=20}, Student{name=猪八 戒, age=20}, Student{name=沙僧, age=27}, Student{name=白龙马, age=21}]
------------------------------
删除之后
元素个数4
[Student{name=孙悟空, age=20}, Student{name=猪八戒, age=20}, Student{name=沙 僧, age=27}, Student{name=白龙马, age=21}]
------------------------------
遍历元素增强for
Student{name=孙悟空, age=20}
Student{name=猪八戒, age=20}
Student{name=沙僧, age=27}
Student{name=白龙马, age=21}
------------------------------
遍历元素迭代器
Student{name=孙悟空, age=20}
Student{name=猪八戒, age=20}
Student{name=沙僧, age=27}
Student{name=白龙马, age=21}
------------------------------
判断元素是否存在
student1是否存在:false
student2是否存在:true
*/
三、List接口与实现类
List接口
-
List子接口
-
特点。有序、有下标、元素可以重复。
-
方法:
- void add(int index,0bject o) //在index位置插入对象o。
- boolean addAll(int index,Collection c) //将一个集合中的元素添加到此集合中的index位置。
- Object get(int index) //返回集合中指定位置的元素。
- List subList(int fromIndex,int toIndex) //返回fromIndex和toIndex之间的集合元素。
-
案例一:
package com.mike.test;
/*
List子接口的使用
1、有序,有下标,可以重复
*/
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.ListIterator;
public class Test {
public static void main(String[] args){
//先创建集合对象
List list = new ArrayList();
//1、添加元素
list.add("苹果");
list.add("小米");
list.add("华为");
list.add(0,"OPPO");
System.out.println("元素个数:"+list.size());
System.out.println(list.toString());
//2、删除元素
list.remove(0);
System.out.println("-----------------------------");
System.out.println("删除之后");
System.out.println("元素个数:"+list.size());
System.out.println(list.toString());
//3、遍历
//3.1、使用for遍历
System.out.println("---------使用for遍历--------------");
for (int i = 0; i < list.size(); i++) {
System.out.println(list.get(i));
}
//3.2、使用增强for
System.out.println("-----------使用增强for-------------");
for (Object object : list) {
System.out.println(object.toString());
}
//3.3、使用迭代器
System.out.println("-----------使用迭代器-------------");
Iterator it = list.iterator();
while (it.hasNext())
System.out.println(it.next());
//3.4、使用列表迭代器,, 和Iterator的区别,ListIterator可以向前或向后遍历,添加、删除、修改元素
System.out.println("-----------使用列表迭代器-------------");
ListIterator lit = list.listIterator();
System.out.println("使用列表迭代器,从前往后迭代");
while (lit.hasNext()) {
System.out.println(lit.nextIndex()+":"+lit.next());
}
System.out.println("使用列表迭代器,从从后往前迭代");
while (lit.hasPrevious()) {
System.out.println(lit.previousIndex()+":"+lit.previous());
}
//4判断
System.out.println("==================");
System.out.println(list.contains("苹果"));
System.out.println(list.isEmpty());
//5获取位置
System.out.println("获取华为下角标:"+list.indexOf("华为"));
}
}
/*输出结果
元素个数:4
[OPPO, 苹果, 小米, 华为]
-----------------------------
删除之后
元素个数:3
[苹果, 小米, 华为]
---------使用for遍历--------------
苹果
小米
华为
-----------使用增强for-------------
苹果
小米
华为
-----------使用迭代器-------------
苹果
小米
华为
-----------使用列表迭代器-------------
使用列表迭代器,从前往后迭代
0:苹果
1:小米
2:华为
使用列表迭代器,从从后往前迭代
2:华为
1:小米
0:苹果
==================
true
false
获取华为下角标:2
*/
案例二:
List集合添加基本数据类型(装箱操作)
package com.mike.test;
/*
List子接口的使用
1、有序,有下标,可以重复
*/
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.ListIterator;
public class Test {
public static void main(String[] args){
//先创建集合对象
List list = new ArrayList();
//1、添加数字类型(由于集合不能添加基本数据类型,所以这里隐藏了一个步骤,叫装箱)
//jdk1.5之后,自动装箱
list.add(10);
list.add(20);
list.add(30);
list.add(40);
list.add(50);
System.out.println("元素个数:"+list.size());
System.out.println(list.toString());
//2、删除
//list.remove(0);//删除下标为0的元素
list.remove(new Integer(20));//由于20是基本数据类型,所以这里必须转换为Integer类型
System.out.println("元素个数:"+list.size());
System.out.println(list.toString());
//3、补充方法subList:()返回子集合,含头不含尾
List subList = list.subList(1, 3);
System.out.println(subList.toString());
}
}
/*输出结果
元素个数:5
[10, 20, 30, 40, 50]
元素个数:4
[10, 30, 40, 50]
[30, 40]
*/
List实现类
-
ArrayList【重点】:
- 数组结构实现,查询快,增删慢;
- JDK1. 2版本,运行效率快,线程不安全。
-
Vector:
- 数组结构实现,查询快,增删慢;
- JDK1. 0版本,运行效率慢,线程安全。
-
LinkedList:
- 链表结构实现,增删快,查询慢;
ArrayList的使用
Student类
package com.mike.test;
public class Student {
private String name;
private int age;
public Student() {
}
public Student(String name, int age) {
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
@Override
public String toString() {
return "Student{" + "name=" + name + ", age=" + age + '}';
}
@Override
public boolean equals(Object obj) {
//1.是不是同一个对象
if (this==obj){
return true;
}
//2.是不是为空
if (obj==null){
return false;
}
//3.判断是否是Student类型
if (obj instanceof Student){
Student s =(Student) obj;
//4.比较属性
if (this.name.equals(s.getName())&&this.age==s.getAge()){
return true;
}
}
//5.不满足条件,返回false
return false;
}
}
Test类
package com.mike.test;
/*
ArrayList的使用
存储结构:数组,查找遍历速度快,增删慢
*/
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.ListIterator;
public class Test {
public static void main(String[] args){
//创建集合
ArrayList arrayList = new ArrayList();
//1、添加元素
Student s1 = new Student("刘德华",60);
Student s2 = new Student("张学友",60);
Student s3 = new Student("黎明",55);
Student s4 = new Student("郭富城",56);
arrayList.add(s1);
arrayList.add(s2);
arrayList.add(s3);
arrayList.add(s4);
arrayList.add(s4);
System.out.println("元素个数:"+arrayList.size());
System.out.println(arrayList.toString());
//2、删除元素
//如果像下面这样写,我们并不能删除"刘德华",20这个数据,非要这样删除,只能重写equals方法
//比较创建的对象和集合里面是否为同一个对象,如果数据一样,则认为是同一个对象,允许删除
//arrayList.remove(new Student("刘德华",20));//equals(this==obj)重写equals方法
arrayList.remove(4);
System.out.println("元素个数:"+arrayList.size());
System.out.println(arrayList.toString());
//3、遍历元素【重点】
//3.1、迭代器
System.out.println("---------迭代器遍历------------");
Iterator it = arrayList.iterator();
while (it.hasNext()){
Student s = (Student) it.next();
System.out.println(s.toString());
}
System.out.println("---------列表迭代器遍历------------");
ListIterator lit = arrayList.listIterator();
System.out.println("列表迭代器,从前往后");
while (lit.hasNext()) {
Student s = (Student) lit.next();
System.out.println(lit.previousIndex()+":"+s.toString());//观察最后结果下标
}
System.out.println("列表迭代器,从后往前");
while (lit.hasPrevious()) {
Student s = (Student) lit.previous();
System.out.println(lit.previousIndex()+":"+s.toString());//观察最后结果下标
}
//4、判断
//因为这里的Student类重写了equals方法,所以比较的是内容
System.out.println(arrayList.contains(new Student("郭富城", 56)));
System.out.println("集合是否为空"+arrayList.isEmpty());
//5、查找位置(查找下标)
System.out.println(arrayList.indexOf(s3));
System.out.println(arrayList.indexOf(s1));
}
}
/*输出结果
元素个数:5
[Student{name=刘德华, age=60}, Student{name=张学友, age=60}, Student{name=黎明, age=55}, Student{name=郭富城, age=56}, Student{name=郭富城, age=56}]
元素个数:4
[Student{name=刘德华, age=60}, Student{name=张学友, age=60}, Student{name=黎明, age=55}, Student{name=郭富城, age=56}]
---------迭代器遍历------------
Student{name=刘德华, age=60}
Student{name=张学友, age=60}
Student{name=黎明, age=55}
Student{name=郭富城, age=56}
---------列表迭代器遍历------------
列表迭代器,从前往后
0:Student{name=刘德华, age=60}
1:Student{name=张学友, age=60}
2:Student{name=黎明, age=55}
3:Student{name=郭富城, age=56}
列表迭代器,从后往前
2:Student{name=郭富城, age=56}
1:Student{name=黎明, age=55}
0:Student{name=张学友, age=60}
-1:Student{name=刘德华, age=60}
true
集合是否为空false
2
0
*/
ArrayList源码分析
- 默认容量大小:DEFAULT_CAPACITY=10;
- 注意:如果没有向集合中添加任何元素时,容量为0
- 添加第一个元素之后容量变成10,后面如果需要再次扩容,那么扩容大小是原来的1.5倍
- 0-->10-->15~~
存放元素的数组:elementData
Vector的使用
向量集合Vector
package com.mike.test;
/*
Vector的使用
存储结构:数组,查找遍历速度快,增删慢
*/
import java.util.Enumeration;
import java.util.Vector;
public class Test {
public static void main(String[] args){
//1、创建集合,实例化vector
Vector vector = new Vector();
//2、添加元素
vector.add("草莓");
vector.add("苹果");
vector.add("西瓜");
System.out.println("元素个数:"+ vector.size());
System.out.println(vector.toString());
//3、删除
// vector.remove(0);//根据下标移除
// vector.remove("西瓜");//根据字段移除
// vector.clear();//将元素从集合中全部移除
//4、遍历
//可以使用for,增强for,迭代器,列表迭代器
//这里我们使用它特有的遍历方式:枚举器(和迭代器功能一模一样,不同名字罢了)
System.out.println("------枚举器遍历元素------");
Enumeration en = vector.elements();
while (en.hasMoreElements()) {
String o = (String) en.nextElement();
System.out.println(o);
}
//5、判断
System.out.println("判断是否有西瓜:"+vector.contains("西瓜"));
System.out.println("判断集合是否为空:"+vector.isEmpty());
//6、vector其他方法
//firstElement、lastElement、elementAt()
}
}
/*输出结果
元素个数:3
[草莓, 苹果, 西瓜]
------枚举器遍历元素------
草莓
苹果
西瓜
判断是否有西瓜:true
判断集合是否为空:false
*/
LinkedList的使用
package com.mike.test;
/*
LinkedList的使用
存储结构:双向链表
链表结构实现,增删快,查询慢;
*/
import java.util.Iterator;
import java.util.LinkedList;
import java.util.ListIterator;
public class Test {
public static void main(String[] args){
//1、创建集合,实例化vector
LinkedList linkedList = new LinkedList();
//2、添加元素
Student s1 = new Student("小明",20);
Student s2 = new Student("小红",18);
Student s3 = new Student("小军",19);
linkedList.add(s1);
linkedList.add(s2);
linkedList.add(s3);
System.out.println("元素个数:"+linkedList.size());
System.out.println(linkedList.toString());
//3、删除元素
// linkedList.remove(s1);
// linkedList.clear();//清除集合中所有元素
// System.out.println("删除对象s1之后元素个数:"+ linkedList.size());
// System.out.println(linkedList.toString());
//4、遍历
//4.1使用for遍历
System.out.println("--------使用for遍历-----------");
for (int i = 0; i < linkedList.size(); i++) {
System.out.println(linkedList.get(i));
}
//4.2使用增强for遍历
System.out.println("--------使用增强for遍历-----------");
for (Object o : linkedList) {
Student s = (Student) o;
System.out.println(s.toString());
}
//4.3使用迭代器遍历
System.out.println("--------使用迭代器遍历-----------");
Iterator it = linkedList.iterator();
while (it.hasNext()) {
Student s = (Student) it.next();
System.out.println(s);
}
//4.4使用列迭代器
System.out.println("--------使用列迭代器遍历-----------");
//从后往前
ListIterator lit = linkedList.listIterator();
while (lit.hasNext()) {
Student s = (Student) lit.next();
System.out.println(s);
}
//5、判断
System.out.println("判断对象s1是否存在:"+linkedList.contains(s1));
System.out.println("判断元素是否为空:"+linkedList.isEmpty());
//6、获取
System.out.println("获取s2的下标位置:"+linkedList.indexOf(s2));
}
}
/*输出结果
元素个数:3
[Student{name=小明, age=20}, Student{name=小红, age=18}, Student{name=小军, age=19}]
--------使用for遍历-----------
Student{name=小明, age=20}
Student{name=小红, age=18}
Student{name=小军, age=19}
--------使用增强for遍历-----------
Student{name=小明, age=20}
Student{name=小红, age=18}
Student{name=小军, age=19}
--------使用迭代器遍历-----------
Student{name=小明, age=20}
Student{name=小红, age=18}
Student{name=小军, age=19}
--------使用列迭代器遍历-----------
Student{name=小明, age=20}
Student{name=小红, age=18}
Student{name=小军, age=19}
判断对象s1是否存在:true
判断元素是否为空:false
获取s2的下标位置:1
*/
LinkedList源码分析
- int size:集合的大小
- Node first;:链表的头节点
- Node last:链表的尾节点
void linkLast(E e) {
final Node<E> l = last;
final Node<E> newNode = new Node<>(l, e, null);
last = newNode;
if (l == null)
first = newNode;
else
l.next = newNode;
size++;
modCount++;
}
private static class Node<E> {
E item;
Node<E> next;
Node<E> prev;
Node(Node<E> prev, E element, Node<E> next) {
this.item = element;
this.next = next;
this.prev = prev;
}
}
不同结构实现方式
四、泛型和工具类
介绍泛型
-
Java泛型是JDK1.5中引入的一个新特性,其本质是参数化类型,把类型作为参数传递。
-
常见形式有泛型类、泛型接口、泛型方法。
-
语法:
- <T....> T称为类型占位符,表示一种引用类型。
-
好处:
- (1)提高代码的重用性
- (2)防止类型转换异常,提高代码的安全性
创建泛型类
案例一:
package com.mike.test;
/*
泛型类
语法:类名<T,E,K...>
T是类型占位符,表示一种引用类型,如果编写多个,用逗号隔开
*/
public class Test<T> {
//使用泛型T
//1、创建变量
T t;
//2、作为方法的参数
public void show(T t){
System.out.println(t);
}
//3、泛型作为方法的返回值
public T getT(){
return t;
}
public static void main(String[] args){
//使用泛型类创建对象
//注意: 1泛型只能使用引用类型,2不同泛型类型对象之间不能相互赋值
Test<String> test1 = new Test<String>();//jdk1.7之后后面尖括号可写可不写
test1.t = "hello";
test1.show("大家好!");
String t = test1.getT();
System.out.println(t);
Test<Integer> test2 = new Test<Integer>();
test2.t = 100;
test2.show(200);
Integer t1 = test2.getT();
System.out.println(t1);
}
}
/*输出结果
大家好!
hello
200
100
*/
泛型接口
MyInterface接口
package com.mike.test;
/*
泛型接口
语法:接口名<T,E,K...>
注意:不能使用泛型创建静态常量
T是类型占位符,表示一种引用类型,如果编写多个,用逗号隔开
*/
public interface MyInterface<T> {
String name = "张三";
T server(T t);
}
MyInterfaceImpl类
package com.mike.test;
public class MyInterfaceImpl<T> implements MyInterface<T> {
@Override
public T server(T t) {
System.out.println(t);
return t;
}
}
MyInterfaceImpl2类
package com.mike.test;
public class MyInterfaceImpl2 implements MyInterface<String> {
@Override
public String server(String s) {
System.out.println(s);
return s;
}
}
Test类
package com.mike.test;
/*
泛型类
语法:类名<T,E,K...>
T是类型占位符,表示一种引用类型,如果编写多个,用逗号隔开
*/
public class Test implements MyInterface<String> {
public static void main(String[] args) {
Test test = new Test();
test.server("你好!中国!");
MyInterfaceImpl<Integer> impl = new MyInterfaceImpl<>();
impl.server(200);
MyInterfaceImpl2 impl2 = new MyInterfaceImpl2();
impl2.server("HelloWord");
}
@Override
public String server(String s) {
System.out.println(s);
return s;
}
}
/*输出结果
你好!中国!
200
HelloWord
*/
泛型方法
MyGenericMethod类
package com.mike.test;
/*
泛型方法
语法: <T>返回值类型
*/
public class MyGenericMethod {
//泛型方法
public <T> T show(T t){
System.out.println("泛型方法:"+t);
return t;
}
}
Test类
package com.mike.test;
public class Test {
public static void main(String[] args) {
//泛型方法的调用
MyGenericMethod myGenericMethod = new MyGenericMethod();
myGenericMethod.show("中国加油");
myGenericMethod.show(200);
myGenericMethod.show(3.14);
}
}
/*输出结果
泛型方法:中国加油
泛型方法:200
泛型方法:3.14
*/
泛型集合
-
概念:参数化类型、类型安全的集合,强制集合元素的类型必须一致。
-
特点:
- 编译时即可检查,而非运行时抛出异常。
- 访问时,不必类型转换(拆箱)。
- 不同泛型之间引用不能相互赋值,泛型不存在多态。
package com.mike.test;
import java.util.ArrayList;
import java.util.ListIterator;
public class Test {
public static void main(String[] args) {
ArrayList<String> arrayList = new ArrayList<String>();
arrayList.add("猪八戒");
arrayList.add("孙悟空");
for (String s : arrayList) {
System.out.println(s);
}
System.out.println("------------------------------");
ArrayList<Student> studentArrayList = new ArrayList<Student>();
Student student1 = new Student("沙僧", 21);
Student student2 = new Student("唐僧", 20);
studentArrayList.add(student1);
studentArrayList.add(student2);
System.out.println("列迭代器遍历");
ListIterator<Student> stl = studentArrayList.listIterator();
while (stl.hasNext()) {
Student s = stl.next();
System.out.println(s.toString());
}
}
}
/*输出结果
猪八戒
孙悟空
------------------------------
列迭代器遍历
Student{name=沙僧, age=21}
Student{name=唐僧, age=20}
*/
五、Set接口与实现类
Set接口
- 特点:无序、无下标、元素不可重复。
- 方法:全部继承自Collection中的方法。
Set的使用
package com.mike.test;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Set;
/*
测试Set接口的使用
特点: (1) 无序、没有下标(2)不能重复
*/
public class Test {
public static void main(String[] args) {
//创建集合
Set<String> set = new HashSet<String>();
//1.添加数据
set.add("苹果");
set.add("菠萝");
set.add("草莓");
System.out.println("数据个数:"+set.size());
System.out.println(set.toString());
//2.删除
set.remove("苹果");
System.out.println("数据个数:"+set.size());
System.out.println(set.toString());
//3、遍历【重点】
//3.1、增强for
System.out.println("--------增强for-------");
for (String s : set) {
System.out.println(s);
}
//3.2、迭代器
System.out.println("--------迭代器-------");
Iterator<String> it = set.iterator();
while (it.hasNext()) {
String s = it.next();
System.out.println(s);
}
//4判断
System.out.println("Set集合里是否有华为:"+set.contains("菠萝"));
System.out.println("Set集合是否为空:"+set.isEmpty());
}
}
/*输出结果
数据个数:3
[苹果, 草莓, 菠萝]
数据个数:2
[草莓, 菠萝]
--------增强for-------
草莓
菠萝
--------迭代器-------
草莓
菠萝
Set集合里是否有华为:true
Set集合是否为空:false
*/
Set实现类
-
HashSet 【重点】:
- 基于HashCode实现元素不重复。
- 当存入元素的哈希码相同时,会调用equals进行确认, 如结果为true, 则拒绝后者存入。
-
TreeSet:
- 基于排列顺序实现元素不重复。
- 实现了SortedSet接口, 对集合元素自动排序。
- 元素对象的类型必须实现Comparable接口,指定排序规则。
- 通过CompareTo方法确定是否为重复元素。
HashSet使用案例一:
package com.mike.test;
/*
HashSet集合的使用
存储结构:哈希表(数组+链表+红黑树(jdk1.8之后))
*/
import java.util.HashSet;
import java.util.Iterator;
public class Test {
public static void main(String[] args) {
//新建集合
HashSet<String> hashSet = new HashSet<String>();
//1、添加元素
hashSet.add("刘德华");
hashSet.add("梁朝伟");
hashSet.add("林志玲");
hashSet.add("周润发");
System.out.println("元素个数:"+hashSet.size());
System.out.println(hashSet.toString());
//2、删除数据
hashSet.remove("刘德华");
System.out.println("元素个数:"+hashSet.size());
System.out.println(hashSet.toString());
//3、遍历操作
//3.1、增强for
System.out.println("------增强for-------");
for (String s : hashSet) {
System.out.println(s);
}
//3.2、使用迭代器
System.out.println("-------使用迭代器--------");
Iterator<String> it = hashSet.iterator();
while (it.hasNext()) {
String s = it.next();
System.out.println(s);
}
//4判断
System.out.println("该集合中是否添加了郭富城:"+hashSet.contains("郭富城"));
System.out.println("该集合是否为空:");
}
}
/*输出结果
元素个数:4
[林志玲, 梁朝伟, 周润发, 刘德华]
元素个数:3
[林志玲, 梁朝伟, 周润发]
------增强for-------
林志玲
梁朝伟
周润发
-------使用迭代器--------
林志玲
梁朝伟
周润发
该集合中是否添加了郭富城:false
该集合是否为空:
*/
HashSet使用案例二:
Person类
package com.mike.test;
public class Person {
private String name;
private int age;
public Person() {
}
public Person(String name, int age) {
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
@Override
public int hashCode() {
int n1 = this.name.hashCode();
int n2 = this.age;
return n1+n2;
}
@Override
public boolean equals(Object obj) {
if (this==obj){
return true;
}
if (obj==null){
return false;
}
if (obj instanceof Person){
Person p =(Person) obj;
if (this.name.equals(p.getName())&&this.age==p.getAge()){
return true;
}
}
return false;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
}
Test类
package com.mike.test;
/*
HashSet集合的使用
存储结构:哈希表(数组+链表+红黑树(jdk1.8之后))
存储过程:(重复依据)
(1)根据hashcode计算保存的位置,如果此位置为空,则直接保存,如果不为空执行第二步。
(2)再执行equals方法,如果equals方法为true,则认为是重复,否则,形成链表
*/
import java.util.HashSet;
import java.util.Iterator;
public class Test {
public static void main(String[] args) {
//新建集合
HashSet<Person> hashSet = new HashSet<Person>();
//1、添加元素
Person p1 = new Person("张三", 18);
Person p2 = new Person("李四", 19);
Person p3 = new Person("王五", 20);
Person p4 = new Person("赵六", 21);
hashSet.add(p1);
hashSet.add(p2);
hashSet.add(p3);
hashSet.add(p4);
System.out.println("元素个数:"+hashSet.size());
System.out.println(hashSet.toString());
//2、删除操作
// hashSet.remove(p1);
//当没有重写hashCode()和equals()方法时,下面这个操作是不能删除对象的
//现在Person类里重写了hashCode()和equals()方法,所以hasSet认为这是集合中的同一个对象
// hashSet.remove(new Person("赵六", 21));
// System.out.println("元素个数:"+hashSet.size());
// System.out.println(hashSet.toString());
// 3、遍历【重点】
// 3.1、增强for
System.out.println("------增强for-------");
for (Person p : hashSet) {
System.out.println(p);
}
//3.2、使用迭代器
System.out.println("-------使用迭代器--------");
Iterator<Person> it = hashSet.iterator();
while (it.hasNext()) {
Person p = it.next();
System.out.println(p);
}
//4判断
// System.out.println("该集合中是否添加了p1:"+hashSet.contains(p1));
System.out.println("该集合中是否添加了p3:"+hashSet.contains(new Person("王五", 20)));
System.out.println("该集合是否为空:"+hashSet.isEmpty());
}
}
/*输出结果
元素个数:4
[Person{name='张三', age=18}, Person{name='王五', age=20}, Person{name='李 四', age=19}, Person{name='赵六', age=21}]
------增强for-------
Person{name='张三', age=18}
Person{name='王五', age=20}
Person{name='李四', age=19}
Person{name='赵六', age=21}
-------使用迭代器--------
Person{name='张三', age=18}
Person{name='王五', age=20}
Person{name='李四', age=19}
Person{name='赵六', age=21}
该集合中是否添加了p1:true
该集合是否为空:false
*/
TreeSet使用
package com.mike.test;
/*
TreeSet集合的使用
存储结构:红黑树
存储过程:(重复依据)
(1)根据hashcode计算保存的位置,如果此位置为空,则直接保存,如果不为空执行第二步。
(2)再执行equals方法,如果equals方法为true,则认为是重复,否则,形成链表
*/
import java.util.Iterator;
import java.util.TreeSet;
public class Test {
public static void main(String[] args) {
//新建集合
TreeSet<String> treeSet = new TreeSet<>();
//1、添加元素
treeSet.add("xyz");
treeSet.add("abc");
treeSet.add("hello");
System.out.println("元素个数:"+treeSet.size());
System.out.println(treeSet.toString());
//2、删除操作
// treeSet.remove("xyz");
// System.out.println("删除之后:"+treeSet.toString());
// System.out.println("元素个数:"+treeSet.size());
// 3、遍历【重点】
// 3.1、增强for
System.out.println("------增强for-------");
for (String p : treeSet) {
System.out.println(p);
}
//3.2、使用迭代器
System.out.println("-------使用迭代器--------");
Iterator<String> it = treeSet.iterator();
while (it.hasNext()) {
String p = it.next();
System.out.println(p);
}
//4判断
System.out.println("该集合中是否添加了abc:"+treeSet.contains("abc"));
System.out.println("该集合是否为空:"+treeSet.isEmpty());
}
}
/*输出结果
元素个数:3
[abc, hello, xyz]
------增强for-------
abc
hello
xyz
-------使用迭代器--------
abc
hello
xyz
该集合中是否添加了abc:true
该集合是否为空:false
*/
用TreeSet集合添加对象
Person类
package com.mike.test;
import java.util.Objects;
public class Person implements Comparable<Person> {
private String name;
private int age;
public Person() {
}
public Person(String name, int age) {
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (!(o instanceof Person)) return false;
Person person = (Person) o;
if (age != person.age) return false;
return name.equals(person.name);
}
@Override
public int hashCode() {
int result = name.hashCode();
result = 31 * result + age;
return result;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
// 先按姓名比,然后再按年龄比
@Override
public int compareTo(Person o) {
int n1 = this.getName().compareTo(o.getName());
int n2 = this.age-o.getAge();
return n1== 0 ? n2 : n1;
}
}
Test类
package com.mike.test;
/*
TreeSet集合的使用
存储结构:红黑树
要求:元素必须要实现Comparable接日, compareTo()方法返回值为0,认为是重复元素
*/
import java.util.Iterator;
import java.util.TreeSet;
public class Test {
public static void main(String[] args) {
//新建集合
TreeSet<Person> treeSet = new TreeSet<Person>();
//1、添加元素
Person p1 = new Person("刘德华", 55);
Person p2 = new Person("谢霆锋", 56);
Person p3 = new Person("郭富城", 57);
Person p4 = new Person("周润发", 58);
treeSet.add(p1);
treeSet.add(p2);
treeSet.add(p3);
treeSet.add(p4);
System.out.println("元素个数:"+treeSet.size());
System.out.println(treeSet.toString());
//2、删除操作
// treeSet.remove(p1);
// treeSet.remove(new Person("周润发", 58));//这样删除也是可以的,因为重写了equals和hashcode
// System.out.println("删除之后:"+treeSet.toString());
// System.out.println("元素个数:"+treeSet.size());
// 3、遍历【重点】
// 3.1、增强for
System.out.println("------增强for-------");
for (Person p : treeSet) {
System.out.println(p);
}
//3.2、使用迭代器
System.out.println("-------使用迭代器--------");
Iterator<Person> it = treeSet.iterator();
while (it.hasNext()) {
Person p = it.next();
System.out.println(p);
}
//4判断
System.out.println("该集合中是否添加了p1:"+treeSet.contains(p1));
System.out.println("该集合是否为空:"+treeSet.isEmpty());
}
}
/*输出结果
元素个数:4
[Person{name='刘德华', age=55}, Person{name='周润发', age=58}, Person{name='谢霆锋', age=56}, Person{name='郭富城', age=57}]
------增强for-------
Person{name='刘德华', age=55}
Person{name='周润发', age=58}
Person{name='谢霆锋', age=56}
Person{name='郭富城', age=57}
-------使用迭代器--------
Person{name='刘德华', age=55}
Person{name='周润发', age=58}
Person{name='谢霆锋', age=56}
Person{name='郭富城', age=57}
该集合中是否添加了p1:true
该集合是否为空:false
*/
Comparator :实现定制比较(比较器)
package com.mike.test;
/*
TreeSet集合的使用
Comparator :实现定制比较(比较器)
Comparable:可比较的
*/
import java.util.Comparator;
import java.util.Iterator;
import java.util.TreeSet;
public class Test {
public static void main(String[] args) {
//创建集合,并指定比较规则
TreeSet<Person> treeSet = new TreeSet<>(new Comparator<Person>() {
@Override
public int compare(Person o1, Person o2) {
int n1 = o1.getAge()-o2.getAge();
int n2 = o1.getName().compareTo(o2.getName());
return n1==0?n2:n1;
}
});
Person p1 = new Person("xyz", 20);
Person p2 = new Person("hello", 22);
Person p3 = new Person("zhangsan", 25);
treeSet.add(p1);
treeSet.add(p2);
treeSet.add(p3);
System.out.println("元素个数:"+treeSet.size());
System.out.println(treeSet.toString());
}
}
/*输出结果
元素个数:3
[Person{name='xyz', age=20}, Person{name='hello', age=22}, Person{name='zhangsan', age=25}]
*/
TreeSet小案例
- 要求:使用TreeSet集合实现字符串按照长度进行排序
- helloworld zhang lisi wangwu beijing xian nanjing
package com.mike.test;
import java.util.Comparator;
import java.util.TreeSet;
//要求:使用TreeSet集合实现字符串按照长度进行排序
//helloworld zhang lisi wangwu beijing xian nanjing
//Comparator接口实现定制比较
public class Demo01 {
public static void main(String[] args) {
//创建集合,并指定比较规则
TreeSet<String> treeSet = new TreeSet<String>(new Comparator<String>() {
@Override
public int compare(String o1, String o2) {
int n1 = o1.length()-o2.length();
int n2 = o1.compareTo(o2);//调用compareTo自己的规则
return n1==0?n2:n1;
}
});
//添加数据
treeSet.add("helloworld");
treeSet.add("zhang");
treeSet.add("lisi");
treeSet.add("wangwu");
treeSet.add("beijing");
treeSet.add("xian");
treeSet.add("nanjing");
System.out.println(treeSet.toString());
}
}
/*输出结果:
[lisi, xian, zhang, wangwu, beijing, nanjing, helloworld]
*/
六、Map接口与实现类
Map体系集合
Map父接口
-
特点:存储一对数据(Key-Value),无序、无下标,键不可重复,值可重复。
-
方法:
- V put(K key,V value) //将对象存入到集合中,关联键值。key重复则覆盖原值。
- Object get (Object key) //根据键获取对应的值。
- Set
//返回所有key。 - Collection
values() //返回包含所有值的Collection集合。 - Set<Map. Entry<K, V> //键值匹配的Set集合。
Map接口的使用
遍历效率:keySet()<entrySet()
package com.mike.test;
/*
Map接口的使用
特点:(1)存储键值对(2)键不能重复,值可以重复(3)无序
*/
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
public class Demo01 {
public static void main(String[] args) {
//创建Map集合
Map<String,String> map = new HashMap<>();
//1、添加元素
map.put("CN","中国");
map.put("US","美国");
map.put("UK","英国");
map.put("FR","法国");
map.put("CA","加拿大");
map.put("IT","意大利");
System.out.println("元素个数:"+map.size());
System.out.println(map.toString());
//2、删除
// map.remove("IT");
// System.out.println("------删除Key=IT后------");
// System.out.println("元素个数:"+map.size());
// System.out.println(map.toString());
//3、遍历
//3.1、使用keySet();
System.out.println("----------1、使用keySet()遍历----------");
Set<String> keySet = map.keySet();
for (String s : keySet) {
System.out.println(s+"="+map.get(s));
}
//3.2、使用entrySet()方法
System.out.println("----------2、使用entrySet()方法遍历----------");
Set<Map.Entry<String, String>> entries = map.entrySet();
for (Map.Entry<String, String> entry : entries) {
System.out.println(entry.getKey()+"="+entry.getValue());
}
//4、判断
System.out.println(map.containsKey("CN"));
System.out.println(map.containsValue("泰国"));
}
}
/*
元素个数:6
{UK=英国, CN=中国, IT=意大利, FR=法国, US=美国, CA=加拿大}
----------1、使用keySet()遍历----------
UK=英国
CN=中国
IT=意大利
FR=法国
US=美国
CA=加拿大
----------2、使用entrySet()方法遍历----------
UK=英国
CN=中国
IT=意大利
FR=法国
US=美国
CA=加拿大
true
false
*/
Map集合的实现类
- HashMap 【重点】
- JDK1. 2版本,线程不安全,运行效率快;
- 允许用null作为key或是value。
- HashMap的无参构造默认初始容量是16,默认加载因子(0.75) 的空HashMap。
加载因子: 加载因子是哈希表在其容量自动增加之前可以达到多满的一种尺度。如果当哈希表中的条目数超出了 加载因子与当前容量的乘积时,则要对该哈希表进行rehash()操作,从而哈希表将具有大约两倍的桶数。
-
Hashtable:
- JDK1.0版本,线程安全,运行效率慢;
- 不允许null作为key或是value。
-
Propertiles:
- Hashtable的子类,要求key和value都是String。通常用于配置文件的读取。
-
TreeMap:
- 实现了SortedMap接口(是Map的子接口),可以对key自动排序。
HashMap的使用
Student类
package com.mike.test;
import java.util.Objects;
public class Student {
private int stuNo;
private String name;
public Student() {
}
public Student(int stuNo, String name) {
this.stuNo = stuNo;
this.name = name;
}
public int getStuNo() {
return stuNo;
}
public void setStuNo(int stuNo) {
this.stuNo = stuNo;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (!(o instanceof Student)) return false;
Student student = (Student) o;
if (stuNo != student.stuNo) return false;
return name.equals(student.name);
}
@Override
public int hashCode() {
int result = stuNo;
result = 31 * result + name.hashCode();
return result;
}
@Override
public String toString() {
return "Student{" +
"stuNo=" + stuNo +
", name='" + name + '\'' +
'}';
}
}
Demo01类
package com.mike.test;
/*
HashMap集合的使用
存储结构:哈希表(数组+链表+红黑树)
使用key可hashcode和equals作为重复
*/
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
public class Demo01 {
public static void main(String[] args) {
//创建Map集合
HashMap<Student,String> students = new HashMap<Student,String>();
//1、添加元素
Student s1 = new Student(001, "孙悟空");
Student s2 = new Student(002, "唐三藏");
Student s3 = new Student(003, "猪八戒");
Student s4 = new Student(004, "沙和尚");
Student s5 = new Student(005, "白龙马");
students.put(s1,"北京");
students.put(s2,"南京");
students.put(s3,"河北");
students.put(s4,"河南");
students.put(s5,"上海");
System.out.println("元素个数:"+students.size());
System.out.println(students.toString());
//2、删除
students.remove(s1);
System.out.println("------删除Key=s1后------");
System.out.println("元素个数:"+students.size());
System.out.println(students.toString());
//3、遍历
//3.1、使用keySet();
System.out.println("----------1、使用keySet()遍历----------");
Set<Student> keySet = students.keySet();
for (Student s : keySet) {
System.out.println(s+"="+students.get(s));
}
//3.2、使用entrySet()方法
System.out.println("----------2、使用entrySet()方法遍历----------");
Set<Map.Entry<Student, String>> entries = students.entrySet();
for (Map.Entry<Student, String> entry : entries) {
System.out.println(entry.getKey()+"="+entry.getValue());
}
//4、判断
System.out.println(students.containsKey(s1));
System.out.println(students.containsValue("上海"));
}
}
/*输出结果
元素个数:5
{Student{stuNo=1, name='孙悟空'}=北京, Student{stuNo=4, name='沙和尚'}=河南, Student{stuNo=3, name='猪八戒'}=河北, Student{stuNo=5, name='白龙马'}=上海, Student{stuNo=2, name='唐三藏'}=南京}
------删除Key=s1后------
元素个数:4
{Student{stuNo=4, name='沙和尚'}=河南, Student{stuNo=3, name='猪八戒'}=河北, Student{stuNo=5, name='白龙马'}=上海, Student{stuNo=2, name='唐三藏'}=南京}
----------1、使用keySet()遍历----------
Student{stuNo=4, name='沙和尚'}=河南
Student{stuNo=3, name='猪八戒'}=河北
Student{stuNo=5, name='白龙马'}=上海
Student{stuNo=2, name='唐三藏'}=南京
----------2、使用entrySet()方法遍历----------
Student{stuNo=4, name='沙和尚'}=河南
Student{stuNo=3, name='猪八戒'}=河北
Student{stuNo=5, name='白龙马'}=上海
Student{stuNo=2, name='唐三藏'}=南京
false
true
*/
Map源码分析
1 static final int DEFAULT_INITIAL_CAPACITY = 1 << 4;/ /hashMap初始容量大小
2 static final int MAXIMUM_CAPACITY = 1 << 30;/ /hashmap的数组最大容量
3 static final float DEFAULT_LOAD_ FACTOR = 0.75f; //默认加载因子
4 static final int TREEIFY_THRESHOLD = 8;//jdk1.8 当链表长度大于8时,调整成红黑数
5 static final int UNTREEIFY_THRESHOLD = 6;; //jdk1.8 当链表长度小于6时,调整成链表
6 static final int MIN.TREEIFY_CAPACITY = 64;//jdk1.8 当链表长度大于8时,并且集合元素个数大于等于64时,调整成红黑数
7 transient Node<K,V>[] table;//哈希表中的数组
8 size;//元素个数
HashMap无参构造
刚创建HashMap之后没有添加元素table=null,size=0。(目的:节省空间)
public HashMap() {
this.loadFactor = DEFAULT_LOAD_FACTOR;//all other fields defaulted
}
put方法
public V put(K key, V value) {
return putVal(hash(key), key, value, false, true);
}
HashMap总结
(1)HashMap刚创建时,table是null,为了节省空间,当添加第一个元素时,table容量调整为16
(2)当元素个数大于阈值(16*0.75=12)时,会进行扩容,扩容后大小为原来的2倍。目的是减少调整元素的个数。
(3)jdk1.8每个链表长度大于8,并且元素个数大于等于64时,会调整为红黑树,目的提高执行效率
(4)jdk1.8当链表长度小于6时,调整成链表
(5)jdk1.8以前,链表是头插入,jdk1.8以后时是尾插入
Hashtable和Propertiles
-
Hashtable
- 此类实现一个哈希表,该哈希表将键映射到相应的值。任何非nul1对象都可以用作键或值。
- 为了成功地在哈希表中存储和获取对象,用作键的对象必须实现hashCode方法和equals 方法。
-
Propertiles
- Properties类表示了一个持久的属性集。Properties 可保存在流中或从流中加载。属性列表中每个键及其对应值都是一个字符串 。
- 一个属性列表可包含另一个属性列表作为它的“默认值”;如果未能在原有的属性列表中搜索到属性键,则搜索第二个属性列表。
这里暂时认识一下Hashtable和Propertiles。
TreeMap的使用
Student类
package com.mike.test;
import java.util.Objects;
public class Student implements Comparable<Student> {
private int stuNo;
private String name;
public Student() {
}
public Student(int stuNo, String name) {
this.stuNo = stuNo;
this.name = name;
}
public int getStuNo() {
return stuNo;
}
public void setStuNo(int stuNo) {
this.stuNo = stuNo;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (!(o instanceof Student)) return false;
Student student = (Student) o;
if (stuNo != student.stuNo) return false;
return name.equals(student.name);
}
@Override
public int hashCode() {
int result = stuNo;
result = 31 * result + name.hashCode();
return result;
}
@Override
public String toString() {
return "Student{" +
"stuNo=" + stuNo +
", name='" + name + '\'' +
'}';
}
@Override
public int compareTo(Student o) {
int n1 = this.stuNo-o.getStuNo();
return n1;
}
}
Demo01类
package com.mike.test;
/*
TreeMap的使用
存储结构:红黑树
*/
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
import java.util.TreeMap;
public class Demo01 {
public static void main(String[] args) {
//创建Map集合
TreeMap<Student,String> treeMap = new TreeMap<Student,String>();
/*或者直接用匿名内部类
TreeMap<Student,String> treeMap = new TreeMap<Student,String>(new Comparator<Student>() {
@Override
public int compare(Student o1, Student o2) {
return 0;//在这里写比较规则
}
});
*/
//1、添加元素
Student s1 = new Student(001, "孙悟空");
Student s2 = new Student(002, "唐三藏");
Student s3 = new Student(003, "猪八戒");
Student s4 = new Student(004, "沙和尚");
Student s5 = new Student(005, "白龙马");
treeMap.put(s1,"北京");
treeMap.put(s2,"南京");
treeMap.put(s3,"河北");
treeMap.put(s4,"河南");
treeMap.put(s5,"上海");
System.out.println("元素个数:"+treeMap.size());
//要实现Student类的compareTo()方法,让Student类继承Comparable
//定制比较规则
System.out.println(treeMap.toString());
//2、删除
// treeMap.remove(s1);
// System.out.println("------删除Key=s1后------");
// System.out.println("元素个数:"+treeMap.size());
// System.out.println(treeMap.toString());
//3、遍历
//3.1、使用keySet();
System.out.println("----------1、使用keySet()遍历----------");
Set<Student> keySet = treeMap.keySet();
for (Student s : keySet) {
System.out.println(s+"="+treeMap.get(s));
}
//3.2、使用entrySet()方法
System.out.println("----------2、使用entrySet()方法遍历----------");
Set<Map.Entry<Student, String>> entries = treeMap.entrySet();
for (Map.Entry<Student, String> entry : entries) {
System.out.println(entry.getKey()+"="+entry.getValue());
}
//4、判断
System.out.println(treeMap.containsKey(s1));
System.out.println(treeMap.containsValue("上海"));
}
}
/*输出结果
元素个数:5
{Student{stuNo=1, name='孙悟空'}=北京, Student{stuNo=2, name='唐三藏'}=南京, Student{stuNo=3, name='猪八戒'}=河北, Student{stuNo=4, name='沙和尚'}=河南, Student{stuNo=5, name='白龙马'}=上海}
----------1、使用keySet()遍历----------
Student{stuNo=1, name='孙悟空'}=北京
Student{stuNo=2, name='唐三藏'}=南京
Student{stuNo=3, name='猪八戒'}=河北
Student{stuNo=4, name='沙和尚'}=河南
Student{stuNo=5, name='白龙马'}=上海
----------2、使用entrySet()方法遍历----------
Student{stuNo=1, name='孙悟空'}=北京
Student{stuNo=2, name='唐三藏'}=南京
Student{stuNo=3, name='猪八戒'}=河北
Student{stuNo=4, name='沙和尚'}=河南
Student{stuNo=5, name='白龙马'}=上海
true
true
*/
Colletions工具类
-
概念:集合工具类,定义了除了存取以外的集合常用方法。
-
方法:
public static void reverse(List<?> list) //反转集合中元素的顺序
public static void shuffle(List<?> list) //随机重置集合元素的顺序
public static void sort(List<T> list) //升序排序(元素类型必须实现Comparable接口)
演示Collections工具类的使用
package com.mike.test;
/*
演示Collections工具类的使用
*/
import java.util.*;
public class Test {
public static void main(String[] args) {
List<Integer> list = new ArrayList<Integer>();
list.add(20);
list.add(3);
list.add(35);
list.add(66);
list.add(50);
//sort排序
System.out.println("-----排序前------");
System.out.println(list.toString());
Collections.sort(list);
System.out.println("-----排序后------");
System.out.println(list.toString());
//binarySearch二分查找(只能用在有序的集合中)
int i = Collections.binarySearch(list, 66);
System.out.println("66的位置:"+i);
//copy复制
List<Integer> list2 = new ArrayList<Integer>();
for (int k = 0; k < list.size(); k++) {
list2.add(0);
}
Collections.copy(list2,list);
System.out.println("-----复制后------");
System.out.println(list2.toString());
//reverse反转
Collections.reverse(list);
System.out.println("-----反转后------");
System.out.println(list.toString());
//shuffle 打乱
Collections.shuffle(list);
System.out.println("-----打乱后------");//每次运行都不一样
System.out.println(list.toString());
//补充:list转成数组
System.out.println("-----list转成数组------");
Integer[] arr = list.toArray(new Integer[0]);
System.out.println("长度:"+arr.length);
System.out.println(Arrays.toString(arr));
//数组转成集合
String[] names = {"张三","李四","王五","赵六"};
for (String name : names) {
System.out.println(name);
}
System.out.println("-----数组转成集合------");
//集合是一个受限集合,不能添加和删除
List<String> strings = Arrays.asList(names);
System.out.println(strings.toString());
//把基本类型数组转成集合时,需要修改为包装类型
Integer[] nums = {100,200,300,400,500};
List<Integer> ints = Arrays.asList(nums);
System.out.println(ints);
}
}
/*输出结果
-----排序前------
[20, 3, 35, 66, 50]
-----排序后------
[3, 20, 35, 50, 66]
66的位置:4
-----复制后------
[3, 20, 35, 50, 66]
-----反转后------
[66, 50, 35, 20, 3]
-----打乱后------
[66, 35, 20, 3, 50]
-----list转成数组------
长度:5
[66, 35, 20, 3, 50]
张三
李四
王五
赵六
-----数组转成集合------
[张三, 李四, 王五, 赵六]
[100, 200, 300, 400, 500]
*/
集合总结
-
集合的概念:
- 对象的容器,和数组类似,定义了对多个对象进行操作的常用方法。
-
List集合:
- 有序、有下标、元素可以重复。 (ArrayList、 LinkedList、 Vector)
-
Set集合:
- 无序、无下标、元素不可重复。 (HashSet、 TreeSet)
-
Map集合:
- 存储一对数据,无序、无下标,键不可重复,值可重复。 (HashMap、 HashTable、 TreeMap)
-
Collections:
- 集合工具类,定义了除了存取以外的集合常用方法。