什么是集合
-
概念:对象的容器,定义了对多个对象进行操作的常用方法。可实现数组的功能。
-
和数组的区别:
1.数组长度固定,集合长度不固定
2.数组可以存储基本类型和引用类型,集合只能存储引用类型
Collection父接口
-
特点:代表一组任意类型的对象,无序、无下标、不能重复
-
方法:
boolean add(Object obj)//添加一个对象。
boolean addAll(Collection c)//将一个集合中的所有对象添加到此集合中
void clear()//清空此集合中的所有对象。
boolean contains(Object o)//检查此集合中是否包含o对象
boolean equals(Object o)//比较此集合是否与指定对象相等。
boolean isEmpty()//判断集合是否为空
boolean remove(Object o)//在此集合中移除o对象
int size()//返回此集合中的元素个数。
Object[] toArray() //将此集合转换成数组。
package Collection; import java.util.ArrayList; import java.util.Collection; import java.util.Iterator; /** * Collection接口的使用 * (1)添加元素 * (2)删除元素 * (3)遍历元素 * (4)判断 * @author 【徐先生】 * */ public class Demo01 { public static void main(String[] args) { //创建集合 Collection collection = new ArrayList(); //(1)添加元素 collection .add("苹果"); collection .add("西瓜"); collection .add("榴莲"); System.out.println("元素个数"+collection .size()); System.out.println(collection ); //(2)删除元素 //collection .remove("榴莲"); //collection .clear(); //System.out.println("删除之后"+collection .size()); //System.out.println(collection ); //(3)遍历元素[重点] //1.使用增强for for (Object object : collection) { System.out.println(object ); } //3.2使用迭代器(迭代器专门用来遍历集合的一种方式) //hasNext();有没有下一个元素 //next();获取下一个元素 //remove();删除当前元素 System.out.println("------------------------------------------------------"); Iterator it = collection.iterator(); while(it.hasNext()) { String s = (String)it.next(); System.out.println(s); //it.remove();删除元素 } System.out.println("元素个数:"+collection.size()); //(3)判断 System.out.println(collection .contains("西瓜"));//判断是否含有某个元素 System.out.println(collection .isEmpty());//判断是否为空 } }
List子接口
-
特点:有序、有下标、元素可以重复
-
方法:
void add(int index,Object o)//在index位置插入对象o。
boolean addAll(int index,Collection c)//将一个集合中的元素添加到此集合中的index位置。
Object get(int index)//返回集合中指定位置的元素。
List subList(int fromIndex,int toIndex)//返回fromIndex和toIndex之间的集合元素。
package Collection;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.ListIterator;
/**
* List接口的使用
* 特点:1有序 有下标 2可重复
* @author 【徐先生】
*
*/
public class Demo03 {
public static void main(String[] args) {
//创建集合对象
List list =new ArrayList<>();
//1.添加元素
list .add("苹果");
list .add("小米");
list .add("华为");
System.out.println("元素个数:"+list.size());
System.out.println(list);
//2.删除元素
// list.remove("苹果");
// System.out.println("删除之后"+list.size());
// System.out.println(list);
//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);
}
//3.3使用迭代器
Iterator it = list.iterator();
System.out.println("------------使用迭代器从前往后--------------");
while (it.hasNext()) {
System.out.println(it.next());
}
//3.4使用列表迭代器,和Iterator的区别,可以向前向后遍历,添加,删除,修改元素
System.out.println("------------使用列表迭代器从前往后--------------");
ListIterator lit = list .listIterator();
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(list.contains("苹果"));
System.out.println(list .isEmpty());
//5获取位置
System.out.println(list .indexOf("华为"));
}
}
package Collection;
import java.util.ArrayList;
import java.util.List;
import javax.security.auth.Subject;
/**
* List的使用
* @author 【徐先生】
*
*/
public class Demo04 {
public static void main(String[] args) {
//创建集合
List list = new ArrayList();
//添加数据(自动装箱)
list .add(20);
list .add(30);
list .add(40);
list .add(50);
list .add(60);
System.out.println("元素个数:"+list .size());
System.out.println(list);
//2删除操作
// list.remove((Object) 20);
// list .remove(new Integer(30));
// System.out.println("删除元素:"+list .size());
//3补充方法subList,返回子集合,含头不含尾
List sub = list.subList(1, 3);
System.out.println(sub);
}
}
List实现类
-
Array List【重点】:
数组结构实现,查询快、增删慢;
JDk1.2版本,运行效率快、线程不安全。
-
Vector:
数组结构实现,查询快、增删慢;
JDK1.0版本,运行效率慢、线程安全。
-
Linked List:
链表结构实现,增删快,查询慢。
package Collection;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.ListIterator;
/**
* ArrayList的使用
* 存储结构;数组,查找遍历速度快,查找,增删慢
* @author 【徐先生】
*
*/
public class Demo05 {
public static void main(String[] args) {
//创建集合
ArrayList arrayList = new ArrayList<>();
//1.添加元素
Student s1 = new Student("刘德华",20);
Student s2 = new Student("郭富城",22);
Student s3 = new Student("梁朝伟",18);
arrayList .add(s1);
arrayList .add(s2);
arrayList .add(s3);
System.out.println("元素个数:"+arrayList .size());
System.out.println(arrayList );
//2.删除元素
// arrayList .remove(s1);
// System.out.println("删除之后:"+arrayList );
// arrayList .remove(new Student("梁朝伟",18));
// System.out.println("删除之后:"+arrayList );
//3.遍历元素【重点】
//3.1使用迭代器
System.out.println("-------------使用迭代器------------");
Iterator it = arrayList .iterator();
while (it.hasNext()) {
Student s = (Student)it.next();
System.out.println(s);
// System.out.println(it.next());
}
//3.2列表迭代器
ListIterator lit = arrayList .listIterator();
while (lit.hasNext()) {
System.out.println(lit.next());
}
System.out.println("--------------反向---------------");
while (lit.hasPrevious()) {
System.out.println(lit.previous());
// Student s = (Student)lit.previous();
// System.out.println(s);
}
//4.判断
System.out.println(arrayList .contains(new Student("刘德华",20)));
System.out.println(arrayList .isEmpty());
//5查找
System.out.println(arrayList .indexOf(s1));
}
}
package Collection;
/**
* 学生类
*/
public class Student {
private String name;
private int age;
public Student() {
// TODO Auto-generated constructor stub
}
public Student(String name, int age) {
super();
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;
}
}
//不满足条件返回false
return false ;
}
}
ArrayList源码分析
private static final int DEFAULT_CAPACITY = 10;默认容量
transient Object[] **elementData;**存放元素的数组
private int size;实际元素个数
Vector:
- 数组结构实现,查询快,增删慢;
- JDk1.0版本,运行效率慢、线程安全。
package com.xu.c;
import java.util.Enumeration;
import java.util.Vector;
public class Demo01 {
public static void main(String[] args) {
//创建集合
Vector vector = new Vector<>();
//1.添加元素
vector .add("草莓");
vector .add("芒果");
vector .add("西瓜");
System.out.println("元素个数:"+vector .size());
//2.删除
// vector .remove("西瓜");
// vector .clear();
//3.遍历
//使用枚举器
Enumeration en = vector .elements();
while (en.hasMoreElements()) {
String o = (String) en.nextElement();
System.out.println(o);
}
// 4判断
System.out.println(vector .contains("草莓"));
System.out.println(vector .isEmpty());
//其他方法
// first Element lastElement
}
}
LinkedList:
- 链表结构实现,增删快,查询慢。
package com.xu.c;
import java.util.LinkedList;
import java.util.ListIterator;
import Collection.Student;
/**
* LinkedList的使用
* 存储结构:双向链表
* @author 【徐先生】
*
*/
public class Demo02 {
public static void main(String[] args) {
//创建集合
LinkedList linkedList = new LinkedList<>();
Student s1 = new Student("刘德华",20);
Student s2 = new Student("郭富城",22);
Student s3 = new Student("梁朝伟",18);
linkedList .add(s1);
linkedList .add(s2);
linkedList .add(s3);
System.out.println("元素个数:"+linkedList.size());
System.out.println(linkedList );
//2删除
// linkedList .remove(new Student("刘德华",20));
System.out.println(linkedList );
// 3for遍历
for (int i = 0; i < linkedList .size(); i++) {
System.out.println(linkedList.get(i));
}
// 3.2增强for
System.out.println("----------增强for--------------");
for (Object object : linkedList) {
System.out.println(object );
}
// 3.3使用迭代器
ListIterator lit = linkedList.listIterator();
while (lit.hasNext()) {
System.out.println(lit.next());
}
while (lit.hasPrevious()) {
System.out.println(lit.previous());
}
}
}
泛型
-
JAVA泛型是JDK1.5中引入的一个新特性,其本质是参数化类型,把类型作为参数传递。
-
常见形式有泛型类、泛型接口、泛型方法。
-
语法:
<T…>T称为类型占位符,表示一种引用类型。
-
好处:
(1)提高代码的重用性
(2)防止类型转换异常,提高代码的安全性
package com.xu.c;
public class TestGeneric {
public static void main(String[] args) {
// 使用泛型类创建对象
// 注意泛型只能使用引用类型,不同泛型对象之间不能相互赋值
Demo03<String> demo03 = new Demo03<>();
demo03 .t="hello";
demo03.show("大家好,加油");
demo03 .geT();
Demo03<Integer> demo032 = new Demo03<>();
demo032.t=100;
demo032.show(88);
demo032.geT();
}
}
package com.xu.c;
/**
* 泛型类
* 语法、类名<T>
* T是类型占位符,表示一种引用类型,如果写多个使用逗号隔开
* @author 【徐先生】
*
*/
public class Demo03<T> {
// 使用泛型类
// 1.创建变量
T t;
// 2.作为方法的参数
public void show(T t) {
System.out.println(t);
}
// 3.泛型类作为方法返回值
public T geT() {
System.out.println(t);
return t;
}
}
package com.xu.c;
public class TestGeneric {
public static void main(String[] args) {
MyInterfaceImpl impl = new MyInterfaceImpl();
impl.server("雅璐");
MyInterfaceImpl2<Integer> myInterfaceImpl2 = new MyInterfaceImpl2<>();
myInterfaceImpl2 .server(1000);
MyInterfaceImpl2<String> myInterfaceImpl3 = new MyInterfaceImpl2<>();
myInterfaceImpl3.server("哈哈");
}
}
package com.xu.c;
public class MyInterfaceImpl2<T> implements MyInterface<T>{
@Override
public T server(T t) {
System.out.println(t);
return t;
}
}
package com.xu.c;
public class MyInterfaceImpl implements MyInterface<String> {
@Override
public String server(String t) {
System.out.println(t);
return t;
}
}
package com.xu.c;
/**
* 泛型接口
* 语法:接口名<T>
* @author 【徐先生】
*注意不能使用泛型来创建静态常量
* @param <T>
*/
public interface MyInterface<T> {
String name="张三";
T server(T t);
}
package com.xu.c;
/**
* 泛型方法
* 语法<T>返回值类型
*
* @author 【徐先生】
*
*/
public class MyGenericMethod {
//泛型方法
public <T> T show(T t){
System.out.println("泛型方法"+t);
return t;
}
}
System.out.println("--------------------泛型方法--------------------------------");
MyGenericMethod myGenericMethod = new MyGenericMethod();
myGenericMethod .show("中国");
myGenericMethod.show(1314);
myGenericMethod.show(1.02);
泛型集合
-
概念:参数化类型、类型安全的集合、强制集合元素的类型必须一致。
-
特点:
编译时即可检查,而非运行时抛出异常。
访问时,不必类型转换(拆箱)。
不同泛型之间引用不能相互赋值,泛型不存在多态。
package com.xu.c;
import java.util.ArrayList;
import java.util.Iterator;
import Collection.Student;
/**
* 泛型集合
* @author 【徐先生】
*
*/
public class Demo04 {
public static void main(String[] args) {
ArrayList<String> arrayList = new ArrayList<>();
arrayList.add("hello");
arrayList.add("你好");
for (String string : arrayList) {
System.out.println(string );
}
ArrayList<Student> arrayList2 = new ArrayList<>();
Student s1 = new Student("刘德华",20);
Student s2 = new Student("郭富城",22);
Student s3 = new Student("梁朝伟",18);
arrayList2.add(s1);
arrayList2.add(s2);
arrayList2.add(s3);
Iterator<Student> it = arrayList2.iterator();
while (it.hasNext()) {
System.out.println(it.next());
}
}
}
Set子接口
- 特点:无序、无下标、元素不可重复
- 方法:全部继承自Collection中的方法。
Set实现类
-
HashSet【重点】:
.
基于Hash Code计算元素存放位置*
当存入元素的哈希玛相同时,会调用equals进行确认,如结果为true,则拒绝后者存入。 -
TreeSet
package com.xu.c1;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Set;
/**
* 测试set接口的使用
* 特点:1.无序,无下标,2.不能重复
* @author 【徐先生】
*
*/
public class Demo01 {
public static void main(String[] args) {
//创建集合
Set<String> set = new HashSet<>();
// 1.添加数据
set.add("小米");
set.add("苹果");
set.add("华为");
System.out.println("数据个数:"+set.size());
System.out.println(set);
// 2删除数据
// set.remove("小米");
// System.out.println(set);
// 3遍历[重点]
// 3.1使用增强for
for (String string : set) {
System.out.println(string );
}
// 3.2使用迭代器
System.out.println("--------------使用迭代器-----------------");
Iterator<String> it = set.iterator();
while (it.hasNext()) {
System.out.println(it.next());
}
// 4判断
System.out.println(set.contains("华为"));
System.out.println(set.isEmpty());
}
}
package com.xu.c1;
import java.util.HashSet;
import java.util.Iterator;
/**
* HashSet集合的使用
* 存储结构:哈希表(数组+链表+红黑树)
* @author 【徐先生】
*
*/
public class Demo02 {
public static void main(String[] args) {
// 新建集合
HashSet<String> hashSet = new HashSet<>();
// 1.添加元素
hashSet .add("刘德华");
hashSet .add("梁朝伟");
hashSet .add("林志玲");
hashSet .add("周润发");
System.out.println("元素个数:"+hashSet.size());
System.out.println(hashSet);
// 2.删除数据
// hashSet.remove("周润发");
// System.out.println(hashSet );
// 3遍历操作
// 3.1增强for
System.out.println("--------增强for------------");
for (String string : hashSet) {
System.out.println(string );
}
// 3.2迭代器
System.out.println("-----------使用迭代器---------------");
Iterator<String> it = hashSet.iterator();
while (it.hasNext()) {
System.out.println(it.next());
}
// 4判断
System.out.println(hashSet .contains("刘德华"));
System.out.println(hashSet .isEmpty());
}
}
package com.xu.c1;
import java.util.HashSet;
import java.util.Iterator;
/**
* HashSet的使用
* 存储结构:哈希表(数组位置+链表+红黑树)
* 存储过程
* (1)根据hashcode计算保存位置,如果为空,则直接保存,如果不为空执行第二步.
* (2)再执行equals方法,如果equals方法为true,则认为是重复,否则,形成链表
* @author 【徐先生】
*
*/
public class Demo03 {
public static void main(String[] args) {
// 创建集合
HashSet<Person> persons = new HashSet<>();
// 添加数据
Person p1 = new Person("刘德华",20);
Person p2 = new Person("林志玲",18);
Person p3 = new Person("梁朝伟",23);
persons.add(p1);
persons.add(p2);
persons.add(p3);
// persons .add(p3);重复
persons .add(new Person("梁朝伟",23));
System.out.println("元素个数:"+persons .size());
System.out.println(persons );
// 删除
// persons.remove(p1);
// persons .remove(new Person("林志玲",18));
System.out.println("删除之后:"+persons .size());
// 使用增强for
for (Person person : persons) {
System.out.println(person);
}
System.out.println("---------------------------");
// 迭代器
Iterator<Person> it = persons .iterator();
while (it.hasNext()) {
System.out.println(it.next());
}
// 判断
System.out.println(persons .contains(new Person("林志玲",18)));
}
}
package com.xu.c1;
/**
* 人类
* @author 【徐先生】
*
*/
public class Person {
private String name;
private int age;
public Person() {
// TODO Auto-generated constructor stub
}
public Person(String name, int age) {
super();
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 "Person [name=" + name + ", age=" + age + "]";
}
@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + age;
result = prime * result + ((name == null) ? 0 : name.hashCode());
return result;
}
@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
Person other = (Person) obj;
if (age != other.age)
return false;
if (name == null) {
if (other.name != null)
return false;
} else if (!name.equals(other.name))
return false;
return true;
}
/*@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 false;
}
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;
}*/
}
TreeSet
- 基于排列顺序实现元素不重复。
- 实现了SortedSet接口,对集合元素自动排序。
- 元素对象的类型必须实现Comparable接口,指定排序规则。
- 通过CompareTo方法确定是否为重复元素。
package com.xu.c;
import java.util.Iterator;
import java.util.TreeSet;
import com.xu.first.Hello;
/**
* TreeSet的使用
* 存储结构:红黑树
* @author 【徐先生】
*
*/
public class Demo05 {
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);
// 删除
// treeSet .remove("xyz");
// System.out.println("删除之后:"+treeSet .size());
// 3遍历
// 3.1增强for
for (String string : treeSet) {
System.out.println(string );
}
System.out.println("-------------------------------------");
// 3.2使用迭代器
Iterator<String> it = treeSet .iterator();
while (it.hasNext()) {
System.out.println(it.next());
}
// 4判断
System.out.println(treeSet.contains("xyz"));
}
}
package com.xu.c;
import java.util.Iterator;
import java.util.TreeSet;
import com.xu.c1.Person;
/**
* 使用treeSet保存数据
* 存储结构:红黑树
* 要求必须要实现comparable接口,compareTo()方法返回值为0,认为是重复元素
* @author 【徐先生】
*
*/
public class Demo06 {
public static void main(String[] args) {
// 创建集合
TreeSet<Person> persons = new TreeSet<>();
// 1.添加元素
Person p1 = new Person("刘德华",20);
Person p2 = new Person("郭富城",22);
Person p3 = new Person("梁朝伟",18);
Person p4 = new Person("梁朝伟",20);
persons.add(p1);
persons.add(p2);
persons.add(p3);
persons.add(p4);
System.out.println("元素个数:"+persons .size());
System.out.println(persons);
// 删除
persons.remove(p4);
System.out.println("删除之后:"+persons .size());
// 增强for
System.out.println("--------------------");
for (Person person : persons) {
System.out.println(person);
}
System.out.println("----------------------");
// 使用迭代器
Iterator<Person> it = persons .iterator();
while (it.hasNext()) {
System.out.println(it.next());
}
// 判断
System.out.println(persons .contains(p4));
}
}
comparator
package com.xu.c;
import java.util.Comparator;
import java.util.TreeSet;
import com.xu.c1.Person;
/**
* TreeSet集合使用
* Comparator:实现定制比较(比较器)
* Comparable:可比较的
* @author 【徐先生】
*
*/
public class Demo07 {
public static void main(String[] args) {
// 创建集合,并指定比较规则
TreeSet<Person> persons = 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;
}
});
// 1.添加元素
Person p1 = new Person("刘德华",20);
Person p2 = new Person("郭富城",22);
Person p3 = new Person("梁朝伟",18);
Person p4 = new Person("梁朝伟",20);
persons.add(p1);
persons.add(p2);
persons.add(p3);
persons.add(p4);
System.out.println(persons );
}
}
TreeSet集合小案例
package com.xu.c;
import java.util.Comparator;
import java.util.TreeSet;
import org.omg.CosNaming.NamingContextExtPackage.StringNameHelper;
/**
* 要求:使用TreeSet集合实现字符串按照长度进行排序
* helloWorld zhang lisi wangwu beijing xian nanjing
* @author 【徐先生】
*
*/
public class Demo08 {
public static void main(String[] args) {
// 创建集合,并指定比较规则
TreeSet<String> treeSet = new TreeSet<>(new Comparator<String>() {
@Override
public int compare(String o1, String o2) {
int n1=o1.length()-o2.length();
int n2=o1.compareTo(o2);
return n1==0?n2:n1;
}
});
// 添加数据
treeSet .add("helloWord");
treeSet .add("pingguo");
treeSet .add("lisi");
treeSet.add("beijing");
treeSet .add("xian");
treeSet .add("nanjing");
System.out.println(treeSet);
}
}
Map集合概述
Map接口的特点:
- 用于储存任意键值对(Key-Value)
- 键:无序、无下标、不允许重复(唯一)
- 值:无序、无下标、允许重复
Map父接口
- 特点:存储一对数据(Key- Value),无序、无下标、键不可重复,值可重复。
方法:
- V put(K key,V value)//将对象存入到集合中,关联键值。key重复则覆盖原值。
- Object get(Object key)//根据键获取对应的值。
- Set //返回所有key。
- Collection values() //返回包含所有值的Collection集合。
package com.xu.c;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
/**
* Map接口
* 特点:(1)存储键值对(2)键不能重复,值可以重复(3)无序
* @author 【徐先生】
*
*/
public class Demo09 {
public static void main(String[] args) {
// 创建Map集合
Map<String, String> map = new HashMap<>();
// 1添加元素
map.put("cn", "中国");
map.put("uk", "英国");
map.put("usa", "美国");
System.out.println("元素个数:"+map.size());
System.out.println(map );
// 2删除
// map.remove("uk");
System.out.println("删除之后:"+map.size());
// 3遍历
// 3.1使用keySet();
// Set<String> keySet = map.keySet();
for (String key : map.keySet()) {
System.out.println(key+"----"+map.get(key) );
}
// 3.2使用entrySet();
System.out.println("----------");
// Set<Map.Entry<String, String>> entries = map.entrySet();
for (Map.Entry<String, String> entry : map.entrySet()) {
System.out.println(entry.getKey()+"------"+entry.getValue());
// System.out.println(entry);
// 判断
System.out.println(map.containsKey("uk"));
}
}
}
Map集合的实现类
- HashMap【重点】:
- JDK1.2版本,线程不安全,运行效率快;允许使用null 作为key或是value。
package com.xu.c;
import java.util.HashMap;
import java.util.Map;
import Collection.Student;
/**
* HashMap集合的使用
* 存储结构:哈希表(数组+链表+红黑树)
* @author 【徐先生】
*
*/
public class Dmeo10 {
public static void main(String[] args) {
// 创建集合
HashMap<Student, String> students = new HashMap<>();
// 1添加元素
Student s1=new Student("孙悟空",100);
Student s2=new Student("猪八戒",101);
Student s3=new Student("沙和尚",102);
students .put(s1, "北京");
students .put(s2, "上海");
students .put(s3, "杭州");
students .put(s3, "南京");
students .put(new Student("孙悟空",100), "南京");//如果不想添加重复的,需要重写hashCode,equals
System.out.println("元素个数:"+students .size());
System.out.println(students );
// 2删除
students .remove(s1);
System.out.println("删除之后:"+students .size());
// 3遍历
// 3.1KeySet
for (Student key : students.keySet()) {
System.out.println(key+"---------"+students .get(key));
}
// 3.2entrySet();
System.out.println("------------------------entrySet-----------------------------");
for (Map.Entry<Student, String> entries : students .entrySet()) {
System.out.println(entries.getKey()+"---------"+entries .getValue());
}
// 判断
System.out.println(students .containsKey(new Student("沙和尚",102)));
System.out.println(students .containsKey(s2));
}
}
HashMap源码分析
static final int DEFAULT_INITIAL_CAPACITY = 1 << 4; aka 16
//hasMap初始容量大小(2^4)
static final int MAXIMUM_CAPACITY = 1 << 30;
//hashMap数组最大容量
static final float DEFAULT_LOAD_FACTOR = 0.75f;
//默认加载因子(75%)
static final int TREEIFY_THRESHOLD = 8;
//JDK1.8当链表长度大于8时,调整成红黑树
static final int UNTREEIFY_THRESHOLD = 6;
//jdk1.8 当链表长度小于6时,调整成链表
static final int MIN_TREEIFY_CAPACITY = 64;
//jdk1.8 当链表长度大于8时,并且集合元素个数大于等于64时,调整成红黑树
transient Node<K,V>[] table;
//哈希表中的数组
transient int size;
//元素个数
public HashMap() { this.loadFactor = DEFAULT_LOAD_FACTOR; // all other fields defaulted }
无参构造
public V put(K key, V value) { return putVal(hash(key), key, value, false, true); }
put方法
总结
HasMap刚创建时,table是null,为了节省空间;当添加第一个元素时,table调整为16
当元素个数大于阈值(16*0.75=12)时,会进行扩容,扩容后大小为原来的2倍。目的是减少元素的个数
jdk1.8 当每个链表长度大于8,并且元素个数大于等于64时,会调整为红黑树,目的提高执行效率
jdk1.8 当链表长度小于6时,调整成链表
jdk1.8 以前,链表是头插入,jdk1.8以后是尾插入
Hash table
- JDK1.0版本,线程安全,运行效率慢;不允许null作为key或是value。(基本不用了)
Properties
- Hash table的子类,要求key和value都是String。通常用于配置文件的读取。(IO流之后)
TreeMap
- 实现了Sorted Map接口(是Map的子接口),可以对key自动排序。
package com.xu.c1;
import java.util.Comparator;
import java.util.HashMap;
import java.util.Map;
import java.util.TreeMap;
import Collection.Student;
/**
* TreeMap的使用 存储结构:红黑树
*
* @author 【徐先生】
*
*/
public class Demo04 {
public static void main(String[] args) {
// 创建集合
TreeMap<Student, String> treeMap = new TreeMap(new Comparator<Student>() {
@Override
public int compare(Student o1, Student o2) {
int n1= o1.getAge()-o2.getAge();
return n1;
}
});
// 1添加元素
Student s1 = new Student("孙悟空", 100);
Student s2 = new Student("猪八戒", 101);
Student s3 = new Student("沙和尚", 102);
treeMap.put(s1, "北京");
treeMap.put(s2, "上海");
treeMap.put(s3, "深圳");
System.out.println("元素个数:" + treeMap.size());
System.out.println(treeMap );
// 2删除
// treeMap .remove(s1);
// treeMap.remove(new Student("猪八戒",101));
// System.out.println("删除之后:"+treeMap .size());
// 3遍历
// 3.1keyset();
for (Student key : treeMap.keySet()) {
System.out.println(key+"---------"+treeMap .get(key));
}
// 3.2entryset();
for (Map.Entry<Student, String> entry : treeMap .entrySet()) {
System.out.println(entry.getKey()+"-----------"+entry .getValue());
}
// 判断
System.out.println(treeMap .containsKey(new Student("沙和尚",102)));
}
}
Collections工具类
- 概念:集合工具类,定义了除了存取以外的集合常用方法。
- 方法
- public static void reverse(List<?> list) //反转集合中元素的顺序
- public static void shuffle(List<?> list)// 随机重置集合元素的顺序
- public static void sort(List list) //升序排序(元素类型必须实现Comparable接口)
package com.xu.c1;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;
/**
* 演示Collections工具类的使用
* @author 【徐先生】
*
*/
public class Demo05 {
public static void main(String[] args) {
List<Integer> list = new ArrayList<>();
list.add(20);
list.add(5);
list.add(12);
list.add(34);
list.add(30);
list.add(6);
// sort排序
System.out.println("排序之前:"+list);
Collections.sort(list);
System.out.println("排序之后:"+list);
// binarySearch
int i = Collections.binarySearch(list, 5);
System.out.println("下标为:"+i);
// copy复制
List<Integer> dest = new ArrayList<>();
for (int j = 0; j <list.size(); j++) {
dest.add(0);
}
Collections.copy(dest, list);
System.out.println(dest);
// reverse反转
Collections .reverse(list);
System.out.println("反转之后:"+list);
// shuffle打乱
Collections .shuffle(list);
System.out.println("打乱之后:"+list);
// 补充:list转成数组
Integer[] arr = list.toArray(new Integer[0]);
System.out.println(arr.length);
System.out.println(Arrays.toString(arr));
// 数组转成集合
String[] names = {"张三","李四","王五"};
// 注意集合是一个受限集合,不能添加和删除
List<String> list2 = Arrays.asList(names );
System.out.println(list2);
// 基本类型转成集合时需要改为包装类
Integer[] nums = {100,200,300,400,500};
List<Integer> list3 = Arrays.asList(nums);
System.out.println(list3);
}
}
集合总结
- 集合的概念:
- ==对象的容器,和数组类似,定义了对多个对象进行操作的常用方法。==↘
- List集合:
数组结构
双向链表
- ==有序、有下标、元素可重复。(Array List、Linked List、Vector)==⇥
Collections父接口
- Set集合:
哈希表(jdk1.7数组+链表)
jdk1.8之后加入了红黑树,可以实现Comparator接口
- ==无序、无下标、元素不可重复。(Hash Set、TreeSet)==↗
- Map集合:
哈希表
红黑树
- 存储一对数据,无序、无下标、键不可重复,值可重复。(Hash Map、
Hash Table、Tree Map)
- 存储一对数据,无序、无下标、键不可重复,值可重复。(Hash Map、
- Collections:
- 集合工具类,定义了除了存取以外的集合的常用方法。