Java基础——容器

容器简介

  • 用来容纳和管理数据
  • 把容器里面的数据存储在内存而不是磁盘上。

int i=10;
其实i就是一个容器不过只能存储一个数据
下一步可以用数组来存储多个相同类型的数据,但是数据使用不灵活,要指定长度

容器的结构

单例集合

  • 将数据一个一个的进行存储。
  • list接口是有序存储,可重复,动态数组
  • set接口,存储无序,不可重复,相当于集合
    在这里插入图片描述

根接口collection接口(有两个子接口 list和set接口)

接口介绍
  • Collection 是单例集合根接口,它是集中、收集的意思。Collection 接口的两个子接
    口是 List、Set 接口。
  • 由于 List、Set 是 Collection 的子接口,意味着所有 List、Set 的实现类都有下面的方法
collection里面常用的抽象方法

在这里插入图片描述

子接口list接口

  • 有序:有序(元素存入集合的顺序和取出的顺序一致)。List 中每个元素都有索引标记。可以根据元素的索引标记(在 List 中的位置)访问元素,从而精确控制这些元素。
  • 可重复:List 允许加入重复的元素。更确切地讲,List 通常允许满足 e1.equals(e2) 的元素重复加入容器。
常用方法
  • 除了collection里面的方法外还有一些方法

`

Arraylist容器类(list实现类)
  • 是list的接口的实现类,是list存储特征的具体实现
  • 底层是用数组实现的存储,特点:查询效率高,增删效率低,线程不安全
package container;

import java.lang.ProcessBuilder.Redirect.Type;
import java.util.ArrayList;
import java.util.List;

public class ArrayListTest {

	public static void main(String[] args) {

		//实例化ArrayList容器
		List<String> list = new ArrayList<>(); 
		
		//添加元素 collection里面的add 返回一个Boolean
		System.out.println(list.add("孙少聪"));
		list.add(1, "oldlu"); //索引位置不能大于元素的个数,会导致下标越界
		System.out.println(list);
		
		//静态方法for循环遍历
		ArrayListTest.bianli(list);
		
		//删除元素
		//根据索引删除E remove(int index)返回删除元素
		System.out.println(list.remove(1));
		//根据参数的值来删除对应的元素,有则删除返回true,无则返回false
		System.out.println(list.remove("孙少聪"));
		list.add("孙少聪");
		list.add(1, "哈哈哈");
		
		//替换元素 E set(int index,E elment)
		//替换元素的位置一定要准确长度不能超过元素个数
		list.set(1, "喜羊羊");
		
		//清空容器
		list.clear();
		
		//判断容器是否为空
		//isEmpty() 为空返回true不为空返回false
		System.out.println(list.isEmpty());
		
		
		//判断是否包含指定元素 Boolean contains(E elment)
		System.out.println(list.contains("孙少聪"));
		
		//查找失败返回-1
		//查找元素第一次出现的位置
		System.out.println(list.indexOf("孙少聪"));
		//查找元素最后一次出现的位置
		System.out.println(list.lastIndexOf("孙少聪"));
		
		
		
		//将单例集合转换为数组
		//将ArraList转换为Object[]
		//但是不能将转换的数组做迁至类型转换
		list.add("oldlu");
		list.add("孙少聪"); 
		Object[] arr = list.toArray();
		for(int i = 0;i<arr.length;i++){
			String str = (String)arr[i];
			System.out.println(str);
		}
		//将单例集合转换为指定类型的数组
		//但是类型需要参考泛型中的类型
		String[] arr2 = list.toArray(new String[list.size()]);
		for(int i = 0;i<arr.length;i++){
			System.out.println(arr2[i]);
		}
		
		//容器并集操作
		List<String> a = new ArrayList<>(); 
		a.add("a");
		a.add("b");
		a.add("c");
		a.add("f");
		List<String> b = new ArrayList<>(); 
		b.add("b");
		b.add("c");
		b.add("d");
		boolean flag = a.addAll(b); //a已经被改变了
		System.out.println(flag);
		ArrayListTest.bianli(a);
		//容器交集操作
		boolean flag1 = a.retainAll(b);
		System.out.println(flag1);
		ArrayListTest.bianli(a);
		//容器差集操作
		boolean flag2 = a.removeAll(b);
		System.out.println(flag2);
		ArrayListTest.bianli(a);
		
	}
	
	
	//遍历容器中的元素
	public static void bianli(List<String> list) {
		//获取元素 E get(int index)
		//list.size()方法获取list的元素个数
		for(int i=0;i<list.size();i++) {
			System.out.println(list.get(i));
		}
	}
}

Vector容器类(list实现类)
  • 线程安全,效率低
  • 和ArrayList是相同的,都是list接口中的抽象方法做了具体实现
  • 多了一个同步检查,将多个的并行的线程转换为串行
  • 使用和ArrayList一样
package container;

import java.util.Iterator;
import java.util.List;
import java.util.Vector;

public class VectorTest {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		List<String> v = new Vector<>();
		v.add("hjj");
		v.add("ssc");
		v.add("sjj");
		
		v.get(1);
		
		for (int i = 0; i < v.size(); i++) {
			System.out.println(v.get(i));
		}
	}

}

Stack栈容器
  • Vector的一个子类,实现标准的后进先出的栈LIFO
    在这里插入图片描述
  • 方法+小案例(判断符号对称性)
package container;

import java.util.Stack;
import java.util.Vector;

public class StackTest {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		//实例化栈容器
		Stack<String> lale =  new Stack<>();
		
		//将元素添加到栈容器中
		lale.push("a");
		lale.push("b");
		lale.push("c");
		
		//获取栈容器中的元素
		//只能从栈顶取
		String pop = lale.pop();
		System.out.println(pop);
		System.out.println(lale);
		
		//判断栈里面是否为空,是true 否false
		System.out.println(lale.empty());
		
		//查看栈顶元素
		System.out.println(lale.peek());
		
		//返回元素在栈中的位置
		System.out.println(lale.search("a")); //从顶往下数,栈顶是位置1
		
		//判断对称性
		StackTest stackTest = new StackTest();
		stackTest.symmetry();
	}
	
	//匹配符号对称性
	public void symmetry() {
		String  str="...{.....[....(....)...]....}..(....)..[...]...[...]";	
		//实例化Stack
		Stack<String> a = new Stack<>();
		//假设修正
		boolean flag = true;
		//拆分字符串抓取字符
		for (int i = 0; i < str.length(); i++) {
			char c = str.charAt(i);
			if(c == '{') {
				a.push("}");
			}
			if(c == '[') {
				a.push("]");
			}
			if(c == '(') {
				a.push(")");
			}
			if(c=='}' || c==']' || c==')') {
				if(a.empty()) {
					flag=false;
					break;
				}
				String x = a.pop();
				if(x.charAt(0) != c) {
					flag = false;
					break;
				}
			}
		}
		if(!a.empty()) {
			flag = false;
		}
		System.out.println(flag);
	}
	
}

LinkedList容器类(list实现类)
  • 查询效率低,增删效率高,线程不安全
  • 有序,允许重复
  • LinkedList底层双向链表实现存储
  • 查找只能从头查找,节点越多查找效率低
  • 增删不涉及元素移动,直接挂载就行了。

在这里插入图片描述
在这里插入图片描述

package container;

import java.util.LinkedList;
import java.util.List;

public class LinkedListTest {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		List<String> list = new LinkedList<>();
		
		list.add("a");
		list.add("b");
		list.add("c");
		list.add("d");
		
		//遍历链表元素
		for (int i = 0; i < list.size(); i++) {
			System.out.println(list.get(i));
		}
		System.out.println("==========================");
		for (String str : list) {
			System.out.println(str);
		}
		
		System.out.println("================LinkList+++++++++++++++++++++");
		LinkedList<String> linkedList = new LinkedList<>();
		linkedList.addFirst("a");
		linkedList.addFirst("b");
		linkedList.addFirst("c");
		
		linkedList.addLast("a");
		linkedList.addLast("b");
		linkedList.addLast("c");
		for (String str : linkedList) {
			System.out.println(str); //c b a a b c
		}
		
		System.out.println(linkedList.getFirst()); //c
		System.out.println(linkedList.getLast());//c
		System.out.println(linkedList.removeFirst());//c
		System.out.println(linkedList.removeLast());//c
	}

}

子接口set接口

  • 没有新增的方法,方法和Collection保持完全一致
  • 无序,不重复
HashSet容器类(Set接口实现类)
  • HashSet是一个没有重复的元素集合,不保证元素顺序。允许有null元素
  • 底层采用Hash算法实现
  • 线程不安全
package container;

import java.util.HashSet;
import java.util.Set;

public class HashSetTest {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		Set<String> set = new HashSet<>();
		//添加元素
		set.add("ssc");
		set.add("xjj");
		set.add("hjj");
		
		//获取元素
		//set容器中没有索引,所以没有get方法
		for (String string : set) {
			System.out.println(string);
		}
		
		//删除元素
		boolean flag =  set.remove("ssc");
		System.out.println(flag);
		for (String string : set) {
			System.out.println(string);
		}
		
		//大小
		System.out.println(set.size());
	}

}

HashSet存储自定义对象
  • Users
package container;

import java.util.Objects;

public class Users {
	private String username;
	private int userage;
	
	public void setUserage(int userage) {
		this.userage = userage;
	}
	public int getUserage() {
		return userage;
	}
	public void setUsername(String username) {
		this.username = username;
	}
	public String getUsername() {
		return username;
	}
	@Override
	public String toString() {
		// TODO Auto-generated method stub
		return "Users{"+
				"username='"+username+ '\'' + 
				", userage=" + userage +
				'}';
	}
	public Users(String username, int userage) {
		super();
		this.username = username;
		this.userage = userage;
	}
	public Users() {
		super();
		// TODO Auto-generated constructor stub
	}
	@Override
	public int hashCode() {
		return Objects.hash(userage, username);
	}
	@Override
	public boolean equals(Object obj) {
		System.out.println("equas........");
		if (this == obj)
			return true;
		if (obj == null)
			return false;
		if (getClass() != obj.getClass())
			return false;
		Users other = (Users) obj;
		return userage == other.userage && Objects.equals(username, other.username);
	}
	
}

  • HashSetTest
package container;

import java.util.HashSet;
import java.util.Set;

public class HashSetTest {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		Set<String> set = new HashSet<>();
		//添加元素
		set.add("ssc");
		set.add("xjj");
		set.add("hjj");
		
		//获取元素
		//set容器中没有索引,所以没有get方法
		for (String string : set) {
			System.out.println(string);
		}
		
		//删除元素
		boolean flag =  set.remove("ssc");
		System.out.println(flag);
		for (String string : set) {
			System.out.println(string);
		}
		
		//大小
		System.out.println(set.size());
		
		System.out.println("====================自定义存储对象======================");
		Set<Users> set1 = new HashSet<>();
		Users u = new Users("oldlu", 18);
		Users u1 = new Users("oldlu",18);
		set1.add(u);
		set1.add(u1);
		//对比两个hashcode的值
		//在User里面重定义了HashCode和equals方法了之后,两个hashcode的值就相同了
		System.out.println(u.hashCode());
		System.out.println(u1.hashCode());
		for (Users users : set1) {
			System.out.println(users);
		}
	}

}

TreeSet容器类(Set接口实现类)
  • 可以对元素进行排序,不允许重复
  • 底层是TreeMap实现的
  • 排序实现方式:

通过元素自身实现比较规则
通过比较器比较规则

package container;

import java.util.Set;
import java.util.TreeSet;

public class TreeSetTest {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		Set<String> set = new TreeSet<>();
		set.add("c");
		set.add("a");
		set.add("b");
		set.add("a");
		set.add("d");
		for (String string : set) {
			System.out.println(string); // a b c 
		}
	}

}

通过元素自身实现比较规则
  • Users类
//自定义比较规则
	//正数:大 负数:小 0:相等
	@Override
	public int compareTo(Users o) {
		// TODO Auto-generated method stub
		if(this.userage > o.userage) {
			return 1;
		}
		return -1;
	}
  • TreeSetTest类
		Set<Users> set1 = new TreeSet<>();
		Users u = new Users("ssc", 22);
		Users u1 = new Users("xjj", 20);
		set1.add(u);
		set1.add(u1);
		//重写了compareto方法,在USers方法里面
		for (Users users : set1) {
			System.out.println(users);
		}
通过比较器实现比较规则
  • TreeSetTest类
System.out.println("+++++++++++++++++++++++++++++++++++++++++++++++++++");
		//直接将比较器作为参数穿给TreeSet
		Set<Student> set2 = new TreeSet<>(new StudentComparator());
		Student s = new Student("ssc", 11);
		Student s1 = new Student("xjj", 10);
		Student s2 = new Student("ajj", 10);
		set2.add(s1);
		set2.add(s);
		set2.add(s2);
		for (Student student : set2) {
			System.out.println(student);
		}
  • Student类(类似Users类)
package container;

public class Student {
	private String name;
	private int 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 + "]";
	}
	public Student(String name, int age) {
		super();
		this.name = name;
		this.age = age;
	}
	public Student() {
		super();
		// TODO Auto-generated constructor stub
	}
	
	
}

  • StudentComparetor类(比较器)
package container;

import java.util.Comparator;

public class StudentComparator implements Comparator<Student>{
	//定义比较规则
	@Override
	public int compare(Student o1, Student o2) {
		if(o1.getAge() > o2.getAge()){
			return 1;
		}
		if(o1.getAge() == o2.getAge()) {
			return o1.getName().compareTo(o2.getName());
		}
		return -1;
	}
}

单例集合案例

  • 例子用List和Set,创建一个1-10的随机数存储在容器中
  • List
		//产生一个[1,10]的随机数,并将10个随机数存在容器中
		
		List<Integer> list = new ArrayList<>();
		while(true) {
			int num = (int)(Math.random()*10+1);
			if(!list.contains(num)) {
				list.add(num);
			}
			if(list.size()==10) {
				break;
			}
		}
		for (Integer integer : list) {
			System.out.println(integer);
		}
  • Set
		//产生一个[1,10]的随机数,并将10个随机数存在容器中

		Set<Integer> set = new HashSet<>();
		while(true) {
			int num = (int)(Math.random()*10+1);
			set.add(num);
			if(set.size()==10) {
				break;
			}
		}
		for (Integer integer : set) {
			System.out.println(integer);
		}

双例集合

  • 基于key和value的结构存储数据
  • 类似数学中的函数一个x对应一个。
    在这里插入图片描述

与Collerction之间的区别

  • Collection 中的容器,元素是孤立存在的(理解为单身),向集合中存储元素采用一个个元素的方式存储。
  • Map 中的容器,元素是成对存在的(理解为现代社会的夫妻)。每个元素由键与值两部分组成,通过键可以找对所对应的值。
  • Collection 中的容器称为单列集合,Map 中的容器称为双列集合。
  • Map 中的集合不能包含重复的键,值可以重复;每个键只能对应一个值。
  • Map 中常用的容器为 HashMap,TreeMap 等。

常用方法

在这里插入图片描述

HashMap容器类(Map接口的实现类)

  • 底层采用了哈希表存储数据
  • 要求键不能重复,如果发生重复,新的值会替换旧的值。
  • HashMap 在查找、删除、修改方面都有非常高的效率。
package container;

import java.io.ObjectOutputStream.PutField;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;

import javax.swing.plaf.synth.SynthScrollPaneUI;

public class HashMapTest {

	public static void main(String[] args) {
		
		Map<String, String> map = new HashMap<>();
		
		//添加元素 返回被替代的那个value值 键值相同的value会被覆盖
		map.put("name", "孙少聪");
		String value =  map.put("name", "和佳佳");
		System.out.println(value);
		
		//获取元素方法一get
		String val = map.get("name");
		System.out.println(val);
		//获取元素的方法二keySet
		map.put("b", "B");
		map.put("c", "C");
		map.put("d", "D");
		map.put("e", "E");
		Set<String> keys = map.keySet();
		for (String string : keys) {
			String v1 = map.get(string);
			System.out.println(v1);
		}
		System.out.println("================================================================");
		//获取元素的方法三entrySet方法获取
		Set<Map.Entry<String, String>> entrySet = map.entrySet();
		for (Map.Entry<String, String> entry : entrySet) {
			String key = entry.getKey();
			String v = entry.getValue();
			System.out.println(key+"------"+v);
		}	
		System.out.println("================================================================");
		//并集操作 并过来的key相同那么原容器里面的Value会被覆盖掉
		Map<String, String> map2 = new HashMap<>();
		map2.put("f","F");
		map2.putAll(map);
		Set<String> keys2 = map2.keySet();
		for (String key : keys2) {
			System.out.println("key:"+key+"------"+"Value:"+map2.get(key));
		}
		
		System.out.println("================================================================");
		//删除元素
		String v =  map.remove("e");
		Set<String> keys3 = map.keySet();
		for (String key : keys3) {
			System.out.println("key:"+key+"------"+"Value:"+map.get(key));
		}
		
		System.out.println("================================================================");
		//判断key或者Value是否存在
		System.out.println(map.containsKey("aaaaa"));
		System.out.println(map.containsKey("b"));
		System.out.println(map.containsValue("B"));
	}

}

TreeMap容器类(Map接口的实现类)

  • TreeMap 和 HashMap 同样实现了 Map 接口,对于 API 的用法来说是没有区别的
  • TreeMap 是可以对键进行排序的一种容器,在需要对键排序时可选用 TreeMap
  • TreeMap 底层是基于红黑树实现的
  • 在使用 TreeMap 时需要给定排序规则:
    1. 元素自身实现比较规则
    2. 通过比较器实现比较规则
自身比较规则实现排序(Users类参考上面)
//自身比较规则实现比较
		Map<Users,String>  map  =  new  TreeMap<>();
		Users  u1  =  new  Users("oldlu",18);
		Users  u2  =  new  Users("admin",22);
		Users  u3  =  new  Users("sxt",22);
		map.put(u1, "oldlu");
		map.put(u2, "admin");
		map.put(u3, "sxt");
		Set<Users>  keys  =  map.keySet();
		System.out.println(keys);
		for(Users  key  :keys){
			System.out.println(key+"  ---------  "+map.get(key));
		}
外部比较器实现排序(Users类参考上面)
//外部比较器实现排序
		Map<Student,String>  treemap  =  new  TreeMap<>(new StudentComparator());//传入外部比较规则
		Student  s1  =  new  Student("oldlu",18);
		Student  s2  =  new  Student("admin",22);
		Student  s3  =  new  Student("sxt",22);
		treemap.put(s1, "oldlu");
		treemap.put(s2, "admin");
		treemap.put(s3, "sxt");
		Set<Student>  keys1  =  treemap.keySet();
		System.out.println(keys);
		for(Student  key  :keys1){
			System.out.println(key+"  ---------  "+treemap.get(key));
		}

Iterator迭代器接口

  • Collection接口继承了Iterable接口,在该接口中包含一个名为iterator的抽象方法,所有实现了Collection接口的容器类对该方法做了具体实现。
  • iterator方法会返回一个Iterator接口类型的迭代器对象,在该对象中包含了三个方法用于实现对单例容器的迭代处理

Iterator接口方法

boolean hasNext(); //判断游标当前位置是否有元素,如果有返回true,否则返
回false;

Object next(); //获取当前游标所在位置的元素,并将游标移动到下一个位置;

void remove(); //删除游标当前位置的元素,在执行完next后该操作只能执行
一次;

Iterator迭代List接口类型容器

List<String> list = new ArrayList<>();
		list.add("a");
		list.add("b");
		list.add("c");
		//获取元素 
		Iterator<String> iterator = list.iterator();
		System.out.println("=======================================================");
		boolean flag = iterator.hasNext();
		if(flag) {
			String value = iterator.next();
			System.out.println(value);
		}
		System.out.println("=======================================================");
		//方式一:通过while循环
		while(iterator.hasNext()) {
			String value = iterator.next();
			System.out.println(value);
		}
		System.out.println("=======================================================");
		//方式二:for循环
		for(Iterator<String> it = list.iterator();it.hasNext();) {
			String value = it.next();
			System.out.println(value);
		}

Iterator迭代Set接口类型容器

Set<String> set = new HashSet<>();
		set.add("a");
		set.add("b");
		set.add("c");
		Iterator<String> iterator = set.iterator();
		//方式一:while循环
		while(iterator.hasNext()) {
			String value = iterator.next();
			System.out.println(value);
		}
		System.out.println("===============================================");
		//方式二:while循环
		for(Iterator<String> it = set.iterator();it.hasNext();) {
			String value = it.next();
			System.out.println(value);
		}

Iterator迭代器删除元素

		List<String> list = new ArrayList<>();
		list.add("a");
		list.add("b");
		list.add("c");
		list.add("d");
//		int flag = -1;
//		//不要在循环中改变他的长度,尽量在迭代过程中找到想要删除的元素记住他的下表,出来之后在删除
//		for (int i = 0; i < list.size(); i++) {
//			if("c".equals(list.get(i))) {
//				list.remove(2);
//			}
//			System.out.println(list.get(i));
//		}
		for (String str : list) {
			if("c".equals(str)) {
				list.remove(str);
			}
		}
		for (String str : list) {
			System.out.println(str);
		}

Collection工具类

  • Collections 是一个工具类,它提供了对 Set、List、Map 进行排序、填充、查找元素的辅助方法。
  • 该类中所有的方法都为静态方法。

Collection工具类常用方法

在这里插入图片描述

Collection排序和洗牌

List<String> list  = new ArrayList<>();
		list.add("a");
		list.add("b");
		list.add("d");
		list.add("c");
		//通过Collection方法进行排序
		Collections.sort(list);
		for (String str : list) {
			System.out.println(str);
		}
		
		System.out.println("=====================================");
		List<String> list1  = new ArrayList<>();
		list1.add("a");
		list1.add("b");
		list1.add("c");
		list1.add("d");
		//洗牌处理
		Collections.shuffle(list1);
		for (String str : list1) {
			System.out.println(str);
		}
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值