目录
<7> addAll() 把集合的元素拷贝到另一个相同类型的集合编辑
<1> add(int index ,E element) 在集合指定索引位置,插入元素
<2> remove( int index )删除指定索引位置的元素
<3> set(int index , E element) 修改指索引位置的元素
<4> get(int index) 获取指定索引位置的元素
<5>containsValue(object value)
<9>values() 把所有的值存入collection集合
一、Collection集合
首先通过这张图来了解下collection的集合的家族。
1、collection集合的通用方法
<1> add() 添加元素
<2> clear() 清空所有元素
<3> contains() 查看是否包含某个元素
<4> size() 查看集合的大小
<5> isEmpty 判断集合是否为空
<6> toArray() 把集合元素存储到数组中
<7> addAll() 把集合的元素拷贝到另一个相同类型的集合![](https://i-blog.csdnimg.cn/blog_migrate/cccad1d1882c877d42a52fe889676185.png)
示例代码:
package com.wrx;
import java.lang.reflect.Array;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
public class collection {
public static void main(String[] args) {
// collection集合的常用API
Collection<String> list = new ArrayList<>();
// 1.加入元素 :add()
list.add("wrx");
list.add("111");
list.add("222");
list.add("333");
list.add("444");
list.add("333");
System.out.println(list);//输出list的内容(不算遍历)
// 2.清空集合元素 :clear()
// list.clear();
System.out.println(list);
// 3.判断集合是否为空 :isEmpty()
boolean a = list.isEmpty();
System.out.println(a);//结果应该是false,集合非空
// 4.判断集合是否包含某个元素
boolean b = list.contains("wrx");
System.out.println(b);//结果应该为true,集合里包含这个元素
// 5.删除某个元素(根据元素内容):remove
// 这种删除方式,只会删除集合里第一个相同的元素,后面的相同元素保留
boolean c = list.remove("wrx");
System.out.println(c);//结果应该为true,确实删除了这个元素
// 6.获取集合的大小 : size()
System.out.println(list.size());
// 7.集合转换为数组 :toArray()
Object[] array = list.toArray();//把集合转化为object类型的数据,存入数组中
System.out.println(list);
System.out.println(Arrays.toString(array));//输出数组
// 8.集合的数据拷贝 :addAll()
Collection<String> c1 = new ArrayList<>();
Collection<String> c2 = new ArrayList<>();
c1.add("1");
c1.add("2");//此时c1为[1,2]
c2.add("3");
c2.add("4");//此时c2为[3,4]
c1.addAll(c2);//将c2复制进入c1,此时c1为[1,2,3,4]
System.out.println("c1:"+c1); //输出结果 c1:[1,2,3,4]
}
}
2、collection集合的遍历
<1>iterator使用迭代器遍历
当我们创建迭代器对象时候,迭代器对象默认指向索引为0的位置,也就是第一个数据。
(1) next() 取出当前位置的元素,并且将迭代器对象指向下一个位置。
(2) hasNext() 判断当前索引位置是否有元素。
HashSet<String> set = new HashSet<>();
set.add("wrx");
set.add("yll");
set.add("zyf");
set.add("wxy");
Iterator<String> it3 = set.iterator();
while(it3.hasNext()){
System.out.println(it3.next());
}
<2>foreach/增强for循环
(1)增强for既可以遍历数组也可以遍历集合
(2)内部原理是迭代器iterator,相当于迭代器的简化写法
(3)实现Iterator接口的类才可以使用迭代器和增强for,collection已经实现Iterator接口
示例代码:
// 5.使用增强for循环来遍历集合
Collection<String> c = new ArrayList<>();
// 数据填充
c.add("wrx");
c.add("yll");
c.add("zyf");
c.add("wxy");
// 使用增强for:快捷方式 c.for
for (String s : c) {
System.out.println(s);
}
注意:
当我们想修改集合元素时候,只修改拷贝过来的局部变量是不行的。
如果需要修改的话需要使用普通的for循环或者while循环。
// 修改元素内容
ArrayList<String> c2 = new ArrayList<>();
// 数据填充
c2.add("wrx");
c2.add("wxy");
c2.add("yll");
c2.add("zyf");
c2.add("wxy");
// 使用普通for循环遍历修改
for (int i = 0; i < c2.size(); i++) {
if (c2.get(i)=="wrx"){
c2.set(i,"wrx6666");
}
System.out.println(c2.get(i));
}
二、List集合(collection子接口)
1、List集合的特点
2、List集合的独有方法
由于List集合支持索引,所以多了很多List集合独有的方法。
<1> add(int index ,E element) 在集合指定索引位置,插入元素
<2> remove( int index )删除指定索引位置的元素
<3> set(int index , E element) 修改指索引位置的元素
<4> get(int index) 获取指定索引位置的元素
代码示例:
package com.wrx;
import java.util.ArrayList;
import java.util.List;
public class collection_03_List_methods {
public static void main(String[] args) {
// 创建ArrayList集合并且填充数据
List<String> list = new ArrayList<>();
// 1.在指定索引位置添加数据 add( int index , E element)
list.add(0,"wxy");
list.add(1,"wrx");
list.add(2,"zyf");
list.add(3,"yll");
list.add(4,"qw");
System.out.println(list);
for (String s : list) {
System.out.println(s);//集合遍历
}
// 2.删除指定是索引位置元素 remove(int index)
list.remove(4);// 删除了qw
// 3.根据索引获取元素 get(int index)
System.out.println(list.get(1));//获取的应为wrx
// 4.根据索引修改某个位置的元素
list.set(1,"wrx666666");
System.out.println(list.get(1));//输出信息为wrx666666
}
}
3、ArrayList的底层原理
基本原理: ArrayList底层是基于数组实现的,刚开始会创建一个长度为10的数组,有一个变量size,一开始指向0的位置,并且存的元素个数(刚开始是0),每插入一个元素,size后移一位,size里的存的元素个数加一。
如何插入: 如果我们想在索引为2的位置插入数据(如下图),那么需要先把size位置与插入的位置有多远,就先后移动几位,然后遍历2,3位置的元素,往后移动到size之前一位,这时候就可以在2的位置插入元素。
扩容:数组长度为10,总会用完的,当size指向的索引值等于数组的最大长度史,那么就会新建一个长度为15的数组(1.5倍扩容),并且把原本的数组元素迁移过来。
4、LinkedList及其独有方法
<1>addFirst() 列表开头插入元素
<2>addLast() 列表末尾插入元素
<3>getFirst() 获取表头数据
<4>getLast() 获取表尾数据
<5>removeFirst() 移除表头数据
<6>removeLast() 移除表尾据数
代码示例:
package com.wrx;
import java.util.LinkedHashMap;
import java.util.LinkedList;
import java.util.List;
public class collection_04_List_LinkedList {
public static void main(String[] args) {
// 创建LinkedList并且填充数据
LinkedList<String> lk = new LinkedList<>();
// 1.进栈(先进后出): 压入数据 addFirst()
lk.addFirst("wxy");
lk.addFirst("zyf");
lk.addFirst("yll");
lk.addFirst("qw");
lk.addFirst("wrx");//[wrx, qw, yll, zyf, wxy]
System.out.println(lk);//输出的内容[wrx, qw, yll, zyf, wxy]
// 2.获取列表第一个元素 getFirst()
System.out.println(lk.getFirst());//结果为wrx
// 3.获取列表最后一个元素
System.out.println(lk.getLast());//结果为wxy
// 4.出栈 弹出数据 : removeFirst()
lk.removeFirst();//弹出的数据为wrx(后进先出原则)
System.out.println(lk);//输出的集合内容[qw, yll, zyf, wxy]
System.out.println("----------------------------------------");
// 清空数据
lk.clear();
// 1.队列 入队 addLast()
lk.addLast("wxy");
lk.addLast("wrx");
lk.addLast("zyf");
lk.addLast("yll");
System.out.println(lk);//结果为[wxy, wrx, zyf, yll]
// 2.出队列 出队 removeFirst()
lk.removeFirst();//移除的是wxy
System.out.println(lk);//结果为[wrx, zyf, yll]
}
}
5、循环遍历时如何删除元素
注意:增强for循环和lambda表达式都无法完成这一操作。
<1>迭代器:使用迭代器自身的remove()方法
详情请看代码:里面有解释原因
package com.wrx;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
public class collection_05_遍历删除问题 {
public static void main(String[] args) {
// 创建ArrayList集合并且填充数据
List<String> lists = new ArrayList<>();
// 1.在指定索引位置添加数据 add( int index , E element)
lists.add(0,"wxy");
lists.add(1,"wrx");
lists.add(2,"wrx");
lists.add(3,"zyf");
lists.add(4,"yll");
lists.add(5,"qw");
System.out.println(lists);
// 遍历删除wrx
// 方式一:使用迭代器
Iterator<String> it = lists.iterator();
while(it.hasNext()){
String ele = it.next();
if (ele.equals("wrx")){
it.remove();//注意删除的时候,要用迭代器的删除方法(原因如下)
}
}
// 原因:
/**原因:
* 最一开始迭代器指向第一个元素如下
*
* [wxy, wrx, wrx, zyf, yll, qw]
* ^
*
* 但是当调用完next()方法时,获取到当前指向的数据后,迭代器指针就后移一位如下:
* it.next() 执行next()
*
* [wxy, wrx, wrx, zyf, yll, qw]
* ^
*
* 如果我们想删除wxy,如果我们使用集合的remove()方法,就会出错,因为地址已经后移动了
* 并且如果,我们像删除所有wrx,我们会发现两个wrx相邻的会漏删一个,wrx不相邻就报错了
*
* 迭代器的remove()方法可以规避这个问题
*
*/
}
}
<2>普通for循环1:正序删除
package com.wrx;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
public class collection_05_遍历删除问题 {
public static void main(String[] args) {
// 方式二:for循环 (1)正向删除
// 创建ArrayList集合并且填充数据
List<String> list = new ArrayList<>();
// 1.在指定索引位置添加数据 add( int index , E element)
list.add(0,"wxy");
list.add(1,"wrx");
list.add(2,"wrx");
list.add(3,"zyf");
list.add(4,"yll");
list.add(5,"qw");
System.out.println(list);
// 正向删除:删完索引减一
for (int i = 0; i < list.size(); i++) {
if (list.get(i).equals("wrx")){
list.remove(i);
i--;//一定要索引减一,因为删完之后集合后面的数据会向前迁移一位.详情看下面
}
}
System.out.println(list);
/**索引减一原因:
* 当我们的for循环走到i=1时,出现第一个wrx时候
*
* [wxy, wrx, wrx, zyf, yll, qw]
* i的值: ^ 1
*
* 此时的i=1,我们用equals比较后根据索引删除了,第一个wrx确实删除了,但是集合的结构会变化,并且循环继续走到i=2
* [wxy, wrx, zyf, yll, qw]
* i的值: ^ 2
*
* 此时为我们发现,第二个wrx前移了,我们的i增加了1,索引不匹配了因此我们在根据索引取值,就会漏一个wrx
*
*/
}
}
<3>普通for循环1:倒序删除
package com.wrx;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
public class collection_05_遍历删除问题 {
public static void main(String[] args) {
// 方式三:for循环 (2)倒序删除
// 创建ArrayList集合并且填充数据
List<String> list1 = new ArrayList<>();
// 1.在指定索引位置添加数据 add( int index , E element)
list1.add(0,"wxy");
list1.add(1,"wrx");
list1.add(2,"wrx");
list1.add(3,"zyf");
list1.add(4,"yll");
list1.add(5,"qw");
System.out.println(list1);
// 倒序删除
for (int i = list1.size()-1; i >=0; i--) {//此时需要把for循环的顺序反过来,具体看以下解释
if (list1.get(i).equals("wrx")){
list1.remove(i);
}
}
System.out.println(list1);
/**倒序原因:
* 由于是倒叙我们的for循环的i一开始是集合的长度减一
* [wxy, wrx, wrx, zyf, yll, qw]
* i的值: ^ i=5
* 当循环继续到第一个wrx时候i=2
* [wxy, wrx, wrx, zyf, yll, qw]
* i的值: ^ i=2
*
* 我们用i当作索引删除wrx,集合发生变化,被删除的地方的后面的数据会向前移动
* 同时for循环也在进行i也会减1,结果就是现在的情况,刚好i还是指向下一个元素,不会漏掉
* [wxy, wrx, zyf, yll, qw]
* i的值: ^ i=1
* 此时我们又可以根据i当作索引删除也不会漏掉元素
*
*/
}
}
三、set集合
set集合详细见我的Java常见面试题开头部分。
链接如下:
四、Map集合
1、map集合常用API
<1>put(K key , V value)
<2>remove(Object key) 删除键值对元素
<3>clear()清空集合
<4>containsKey(object key)
<5>containsValue(object value)
<6>isEmpty()
<7>size()
<8>keySet() 把所有的键放入set集合
<9>values() 把所有的值存入collection集合
<10>putAll() Map集合的拷贝
代码示例:
package com.wrx.Map;
import java.util.Collection;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
public class Map_01_API {
public static void main(String[] args) {
// 1.创建Map集合
Map<Integer,String> map = new HashMap<>();
// 2.填充数据 put(K key ,V value)
map.put(1,"wxy");
map.put(2,"wrx");
map.put(3,"yll");
map.put(4,"zyf");
System.out.println(map);
// 3.清空集合 clear()
// map.clear();
// System.out.println(map);
// 4.判断集合是否为空 isEmpty()
System.out.println(map.isEmpty());//输出应为false
// 5.根据键取值 get(K key)
System.out.println(map.get(1));//输出结果应为wxy
// 6.根据键删除整个元素 remove(K key)
System.out.println(map.remove(1));//返回的值为被删除的键的值
// 7.判断是否包含某个键 containsKey(K key)
System.out.println(map.containsKey(1));//1已经被删除了,此时返回的应该的是false
// 8.判断是否包含某个值,containsValue( V value )
System.out.println(map.containsValue("wrx"));//wrx没有被删除,所以返回值是true
// 9.获取全部的键 keySet()
Set<Integer> sets = map.keySet();
System.out.println(sets);//返回值为[2,3,4]
// 10.获取全部的值 values()
Collection<String> values = map.values();
for (String value : values) {
System.out.println(value);
}
// 11.集合的拷贝 putAll(Map<T,T> map)
Map<Integer, String> map1 = new HashMap<>();
map1.putAll(map);
System.out.println("map1:"+map1);//map1:{2=wrx, 3=yll, 4=zyf}
System.out.println("map:"+map);//map:{2=wrx, 3=yll, 4=zyf}
}
}
2、Map的遍历
1、通过遍历键取值
package com.wrx.Map;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
import java.util.function.BiConsumer;
public class Map_02_iterator {
public static void main(String[] args) {
// 1.创建Map集合
Map<Integer,String> map = new HashMap<>();
// 2.填充数据 put(K key ,V value)
map.put(1,"wxy");
map.put(2,"wrx");
map.put(3,"yll");
map.put(4,"zyf");
System.out.println(map);
// 遍历方式(一):用键找值
// 1.先把所有的key放进set集合里,遍历set集合,通过key来获取value
Set<Integer> set1 = map.keySet();
// 2.遍历Set集合通过key获取value
for (Integer integer : set1) {
System.out.println(integer+"="+map.get(integer));//通过Key来获取value
}
}
}
2、获取key-value(代码里有详细解释)
package com.wrx.Map;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
import java.util.function.BiConsumer;
public class Map_02_iterator {
public static void main(String[] args) {
// 1.创建Map集合
Map<Integer,String> map = new HashMap<>();
// 2.填充数据 put(K key ,V value)
map.put(1,"wxy");
map.put(2,"wrx");
map.put(3,"yll");
map.put(4,"zyf");
System.out.println(map);
// 遍历方式(二):直接找key-value
// 1.把map集合的数据类型封装成key-value(一个整体)类型的数据
// 使用entrySet()方法,就是把key和value组成一个整体存入entrySet的对象
// Map.Entry<Integer, String>对象都存了一个key-value
// 然后把entrySet对象存入set集合。
Set<Map.Entry<Integer, String>> entries = map.entrySet();
// 2.遍历set集合,通过Map.Entry<Integer, String>的对象获取key和Value
for (Map.Entry<Integer, String> entry : entries) {
Integer key = entry.getKey();
String value = entry.getValue();
System.out.println(key+"====>"+value);
}
/**方式二的解释:
* map集合原本如下
* {1=wxy, 2=wrx, 3=yll, 4=zyf}
* 1: 使用entrySet()方法
* 2: 此时创建entry<T ,T >接口的实现类对象,并且把key-value键值对类型的数据进行封装
* (1=wxy),( 2=wrx), (3=yll),( 4=zyf)
*
* 3: 上图是每个entry对象里面存的数据,然后放进set集合
* set<Map.Entry<Integer, String>> entries
* [(1=wxy),( 2=wrx), (3=yll),( 4=zyf)]
* 此时里面存的是每个Map.Entry<Integer, String>类型的对象
* 4:遍历set集合获取这个封装的entry对象
* 5:根据entry对象使用getKey()和getValue()来获取一对键值
*/
}
}
3、Lambda表达式
JDK1.8以后开始使用
package com.wrx.Map;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
import java.util.function.BiConsumer;
public class Map_02_iterator {
public static void main(String[] args) {
// 1.创建Map集合
Map<Integer,String> map = new HashMap<>();
// 2.填充数据 put(K key ,V value)
map.put(1,"wxy");
map.put(2,"wrx");
map.put(3,"yll");
map.put(4,"zyf");
System.out.println(map);
// 遍历方式(三):Lambda表达式
map.forEach(new BiConsumer<Integer, String>() {
@Override
public void accept(Integer i, String s) {
System.out.println(i+"==========>"+s);
}
});
// 简化模式
map.forEach( (k,v) -> System.out.println(k+"==========>"+v));
}
}