集合
集合类位于java.util 包下,集合类又被称为容器
与数组的区别
- 数组的长度是固定的,集合的长度是可变的
- 数组可以用来存放基本数据类型,集合存放引用类型,不能存放基本数据类型
如何选择
collection
map
黄色的是接口,蓝色的是实现类
接口名称 | 作 用 |
---|---|
Iterator 接口 | 集合的输出接口,主要用于遍历输出(即迭代访问)Collection 集合中的元素,Iterator 对象被称之为迭代器。迭代器接口是集合接口的父接口,实现类实现 Collection 时就必须实现 Iterator 接口。 |
Collection 接口 | 是 List、Set 和 Queue 的父接口,是存放一组单值的最大接口。所谓的单值是指集合中的每个元素都是一个对象。一般很少直接使用此接口直接操作。 |
Queue 接口 | Queue 是 Java 提供的队列实现,有点类似于 List。 |
Dueue 接口 | 是 Queue 的一个子接口,为双向队列。 |
List 接口 | 是最常用的接口。是有序集合,允许有相同的元素。使用 List 能够精确地控制每个元素插入的位置,用户能够使用索引(元素在 List 中的位置,类似于数组下标)来访问 List 中的元素,与数组类似。 |
Set 接口 | 不能包含重复的元素。 |
Map 接口 | 是存放一对值的最大接口,即接口中的每个元素都是一对,以 key➡value 的形式保存。 |
Collection
Set接口和List接口都继承了Collection接口
它们共同的方法有
方法名称 | 说明 |
---|---|
boolean add(E e) | 向集合中添加一个元素,如果集合对象被添加操作改变了,则返回 true。E 是元素的数据类型 |
boolean addAll(Collection c) | 向集合中添加集合 c 中的所有元素,如果集合对象被添加操作改变了,则返回 true。 |
void clear() | 清除集合中的所有元素,将集合长度变为 0。 |
boolean contains(Object o) | 判断集合中是否存在指定元素 |
boolean containsAll(Collection c) | 判断集合中是否包含集合 c 中的所有元素 |
boolean isEmpty() | 判断集合是否为空 |
Iterator iterator() | 返回一个 Iterator 对象,用于遍历集合中的元素 |
boolean remove(Object o) | 从集合中删除一个指定元素,当集合中包含了一个或多个元素 o 时,该方法只删除第一个符合条件的元素,该方法将返回 true。 |
boolean removeAll(Collection c) | 从集合中删除所有在集合 c 中出现的元素(相当于把调用该方法的集合减去集合 c)。如果该操作改变了调用该方法的集合,则该方法返回 true。 |
boolean retainAll(Collection c) | 从集合中删除集合 c 里不包含的元素(相当于把调用该方法的集合变成该集合和集合 c 的交集),如果该操作改变了调用该方法的集合,则该方法返回 true。 |
int size() | 返回集合中元素的个数 |
Object[] toArray() | 把集合转换为一个数组,所有的集合元素变成对应的数组元素。 |
package com.collection;
import java.util.ArrayList;
//import java.util.Map;
//import java.util.Collection;
public class Collection_ {
public static void main(String[] args) {
ArrayList arrayList = new ArrayList();
//添加元素,add(Object )
arrayList.add("huhu");
arrayList.add(10);//add(new Integer(10))
arrayList.add(true);
System.out.println(arrayList);//[huhu, 10, true]
//删除元素,remove()
// arrayList.remove("huhu");
// System.out.println(arrayList);//[10, true]
// arrayList.remove(1);//可以传入索引值
// System.out.println(arrayList);//[10]
//查找元素是否存在,包含
boolean b=arrayList.contains("huhu");
System.out.println(b);//true
//元素的个数
System.out.println(arrayList.size());//3
//判断集合是否为空
System.out.println(arrayList.isEmpty());//False
//清空
arrayList.clear();
System.out.println(arrayList);//[]
//添加多个元素
ArrayList list2=new ArrayList();
list2.add("haha");
list2.add("jiji");
arrayList.addAll(list2);
System.out.println(arrayList);
//
}
}
List
有序的,添加顺序和取出顺序一致,可以重复
后面是否有向上箭头Collection,代表是否继承自Collection接口
ArrayList
- get(index),索引是从0开始
- 可以加入null ,并且可以加入多个
arraylist.add(null);
- 底层是Object的数组
- 使用无参构造器创建的对象的大小是10;使用指定大小的构造器,则初始化为指定大小
- 如需扩容,扩容为原来的1.5倍
-
参考视频:https://www.bilibili.com/video/BV1fh411y7R8?p=511&spm_id_from=pageDriver&vd_source=1fe29350b37642fa583f709b9ae44b35
- 适合改查
- 基本等同于Vector,但是线程不安全;在多线程的情况下不建议使用
Vector
底层也是一个数组,线程同步即线程安全
LinkedList
- 底层实现了双向链表和双向队列的特点
- 可以重复,包括null
- 线程不安全,没有实现同步
- 通常不会使用
Set
- HashSet无序,存储顺序和查询顺序是不一致的(但是取出的顺序是固定的,只有一种)
- 没有索引,遍历方式没有索引
- 不能重复
- 最多只能有一个null
HashSet
import java.util.HashSet;
import java.util.Set;
public class Set_ {
@SuppressWarnings({"all"})
public static void main(String[] args) {
Set set= new HashSet();
System.out.println(set.add("jiji"));//true
System.out.println(set.add("haha"));//true
System.out.println(set.add("huhu"));//true
System.out.println(set.add("jiji"));//false
set.remove("jiji");
System.out.println(set);//[haha, huhu]
set =new HashSet();
System.out.println(set.add(new Dog("tom")));//true
System.out.println(set.add(new Dog("tom")));//true
System.out.println(set);//[Dog{name='tom'}, Dog{name='tom'}]
set =new HashSet();
System.out.println(set.add(new String("haha")));//true
System.out.println(set.add(new String("haha")));//false
System.out.println(set);//[haha]
}
}
class Dog{
private String name;
public Dog(String name) {
this.name = name;
}
@Override
public String toString() {
return "Dog{" +
"name='" + name + '\'' +
'}';
}
}
Hashset的底层就是HahMap
数组+链表+红黑树
扩容
当链表到达8之后,但是table表没到64之前,会把数据继续加到链表后面,同时进行table数组扩容
LinkedHashSet
- LinkedHashSet是HashSet的子类
- Linkedhashset底层是个 Linkedhashmap,底层维护了一个数组+双向链表
- Linkedhashset根据元素的 hashcode值来决定元素的存储位置,同时使用链表维护元素的次序,这使得元素看起来是以插入顺序保存的
- Linkedhashset不允许添重复元素
TreeSet
TreeSet底层是TreeMap
想让TreeSet排序,在创建TreeSet的时候传给它一个Comapretor
不传,就采用默认排序,但是存储的内容要可比较,即同一类型
当传入的两个key经过比较相同时,key不会变,value会变
TreeSet<Object> set = new TreeSet<>();
set.add("bb");
// set.add(1);//报错
set.add("aa");
set.add("cc");
for (Object o : set) {
System.out.println(o);
}
TreeSet set2 = new TreeSet<>(
new Comparator() {
@Override
public int compare(Object o1,Object o2){
return ((String)o2).compareTo((String) o1);
}
}
);
set2.add("bb");
set2.add("aa");
set2.add("cc");
for (Object o : set2) {
System.out.println(o);
}
Iterator
遍历方式(3种)
package com.collection;
import java.util.ArrayList;
import java.util.Iterator;
//import java.util.Map;
//import java.util.Collection;
public class Collection_ {
public static void main(String[] args) {
ArrayList arrayList = new ArrayList();
arrayList.add("huhu");
arrayList.add(10);//add(new Integer(10))
arrayList.add(true);
//遍历数组的迭代器
Iterator iterator = arrayList.iterator();
while(iterator.hasNext()){//需要先判断是否有下一个元素
Object next = iterator.next();
System.out.println(next);
}
//当迭代器指向最后一个元素后,若想再次遍历要重置迭代器
iterator =arrayList.iterator();
while (iterator.hasNext()) {
Object next = iterator.next();
System.out.println(next);
}
//foreach 的增强循环
for (Object a:
arrayList) {
System.out.println(a);
}
//for循环
for (int i = 0; i < arrayList.size(); i++) {
System.out.println(arrayList.get(i));
}
}
}
Map
- 保存具有映射关系的数据,key-value(双列关系)
常用集合
HashMap,HashTable,Properties
常用方法
HashMap hashmap=new HashMap();
hashmap.put("no1","haha");
hashmap.put("no2","jiji");
//hashmap的key不能重复,可以为null,但只能有一个;无序
hashmap.put("no2","mama");//替换机制
//value可以重复,可以为null,可以有多个
hashmap.put("no3","haha");
hashmap.put(null,null);
//get传入key可以得到value
System.out.println(hashmap.get("no2"));
//remove
hashmap.remove("no1");
//size
System.out.println(hashmap.size());
//isEmpty
System.out.println(hashmap.isEmpty());
//clear
hashmap.clear();
//containsKey
hashmap.containsKey("no8");//false
System.out.println(hashmap);
遍历
EntrySet ,keySet,Values中都是保存的地址 为了方便遍历
KeySet只是建立了一个对于HashMapNode中key的引用,其他类似
Map.Entry是一个内部接口,HashMapNode实现了它
package com.map_;
import com.sun.media.sound.RIFFInvalidFormatException;
import java.util.*;
public class method_ {
@SuppressWarnings({"all"})
public static void main(String[] args) {
HashMap hashmap=new HashMap();
hashmap.put("no1","haha");
hashmap.put("no2","jiji");
hashmap.put("no3","haha");
//第一组:遍历所有的 key
Set keySet = hashmap.keySet();
//(1) for增强循环
for (Object key:
keySet) {
System.out.println(hashmap.get(key));
}
//(2) 迭代器
Iterator iterator = keySet.iterator();
while (iterator.hasNext()) {
Object next = iterator.next();
System.out.println(hashmap.get(next));
}
//第二组: 遍历value
Collection values = hashmap.values();
//(1) for增强
for (Object value:
values) {
System.out.println(value);
}
//(2)迭代器
Iterator iterator1 = values.iterator();
while (iterator1.hasNext()) {
Object next = iterator1.next();
System.out.println(next);
}
//第三组: EntrySet 来获取kv
Set set = hashmap.entrySet();
//(1) for增强
for (Object entry:
set) {
Map.Entry me=(Map.Entry)entry;//向下转型
//只有Map.Entry 是public ,想要使用getkey() 必须转换成Map.Entry
System.out.println(me.getKey());
System.out.println(me.getValue());
System.out.println(entry);
}
//(2) 迭代器
Iterator iterator2 = set.iterator();
while (iterator2.hasNext()) {
Object next = iterator2.next();
Map.Entry me=(Map.Entry)next;//向下转型
System.out.println(((Map.Entry<?, ?>) next).getKey());
System.out.println(me.getValue());
System.out.println(next);
}
}
}
HashMap
- key不能重复,value可以重复
- 允许使用null键和null值
- 如果添加相同的key,则会覆盖原来的;等同于修改,key不变,value变
- 底层是Hash表,不能保证映射的顺序
- 线程不安全
- key和value可以保存任意类型的数据,会保存在HashMap$Node中、key常用字符串
对于HashSet,底层就是HashMap,key就是值,Value是一个常量
HashTable
对比
Properties
- Properties类继承自 Hashtable类并且实现了Map接口,也是使用一种键值对的形式来保有数据。
- 他的使用特点和 Hashtable类似
- Properties还可以用于从xw. properties文件中,加数据到 Properties类对象并进行读和修改
- key不能为null
工作后xx. properties文件通常作为配置文件
Properties properties = new Properties();//创建对象
// 加载配置文件
properties.load(new FileReader("D:\\IDEA_file\\Learn_8\\src\\file\\mysql.properties"));
//或者new
properties.put("name","gao");
properties.remove("name");
//把k-v显示到控制台
properties.list(System.out);
String myuser=properties.getProperty("user");
String mypsd=properties.getProperty("password");
System.out.println(mypsd);
//如果该文件没有该键值对,就创建,有就修改
properties.setProperty("user2","tom");
//指定存储位置
properties.store(new FileWriter("D:\\IDEA_file\\Learn_8\\src\\file\\mysql.properties"),null);
mysql.properties
#Thu Feb 24 23:00:28 CST 2022
user=root
password=19790116
user2=tom
ip=192.168.200.1
工具类
java.util.collections
有许多静态方法
ArrayList<String> list = new ArrayList<>();
list.add("aa");
list.add("cc");
list.add("aa");
list.add("dd");
for (Object o : list) {
System.out.print(o+",");
}
System.out.println();
//反转
Collections.reverse(list);
for (Object o : list) {
System.out.print(o+",");
}
System.out.println();
//排序
Collections.sort(list);//等价于 list.sort(String::compareTo);
for (Object o : list) {
System.out.print(o+",");
}
System.out.println();
//统计频率
int count = Collections.frequency(list, "aa");
System.out.println(count);
//打乱
Collections.shuffle(list);
for (Object o : list) {
System.out.print(o+",");
}
System.out.println();
//交换
Collections.swap(list,0,1);
for (Object o : list) {
System.out.print(o+",");
}
System.out.println();
//最大值
String max = Collections.max(list);
System.out.println(max);
//复制
//替换