Map接口
Map接口概述
将键映射到值的对象
一个映射不能包含重复的键
每个键最多只能映射到一个值
Map接口和Collection接口的不同(Collection接口)
Map是双列的,Collection是单列的
Map的键唯一,Collection的子体系Set是唯一的
Map集合的数据结构值针对键有效,跟值无关Collection集合的数据结构是针对元素有效
Map接口成员方法
添加功能
Vput(Kkey,Vvalu将指定的值与该映射中的指定键相关联
import java.util.HashMap;
import java.util.Map;
public class MapTest1 {
public static void main(String[] args) {
//Map是一个接口,不能实例化,借助子类HashMap来实例化
Map map = new HashMap<>();
//V put(K key,V value) 将指定的值与该映射中的指定键相关联
map.put('充电器','手机');
map.put('电脑','鼠标');
System.out.println(map.put('电脑','键盘')); //如果插入的键一样,值会被覆盖,返回的是被覆盖的值
System.out.println(map);
}
}
删除功能
Vremove(Objectkey)如果存在,从该Map中删除一个键的映射
map.remove('电脑');
voidclear()从该Map中删除所有的映射
map.clear();
判断功能
booleancontainsKey(Objectkey)如果此映射包含指定键的映射,则返回true
//boolean containsKey(Object key) 如果此映射包含指定键的映射,则返回true
System.out.println(map);
System.out.println(map.containsKey('充电器'));
booleancontainsValue(Objectvalu如果此Map将一个或多个键映射到指定的值,则返回true。
map.containsValue('手机')
booleanisEmpty()如果此Map不包含键值映射,则返回true
map.isEmpty();//判断是否有键值对,有返回true,无false
获取功能
Vget(Objectkey)返回指定键所映射的值,或null如果此映射包含该键的映射
System.out.println(map.get('充电器'));
Set
Set set=map.keySet();
//遍历
for (String s:set){
System.out.println(s);
}
Collection
//Collection values() 返回此Map中包含的值的Collection视图
Collection value =map.values();
for (String s :value){
System.out.println(s);
}
Set
//Set> entrySet() 获取Map中所有的元素,元素的类组成是由一个键和一个值组成
Set> entries = map.entrySet();
for (Map.Entry s :entries){
System.out.println(s);
}
长度功能
intsize()返回此Map中键值映射的数量
int size = map.size();
System.out.println(size); //结果为2,取决于里面有多少个键值对
Map集合遍历
方式根据键找值
获取所有键的集合
遍历键的集合,获取到每一个键
根据键找值
例:
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
public class MapTest2 {
public static void main(String[] args) {
//创建集合对象
Map map = new HashMap<>();
//向集合添加元素
map.put(11,'qew');
map.put(23,'qew');
map.put(33,'sfs');
map.put(22,'asf');
//遍历
Set set = map.keySet(); //获取到每一个键
for (Integer s:set){
String s1 = map.get(s); //获取到每一个键对应的值
System.out.println(s+':'+s1);
}
}
}
方式根据键值对对象找键和值
获取所有键值对对象的集合
遍历键值对对象的集合,获取到每一个键值对对象
根据键值对对象找键和值
//创建集合对象
Map map = new HashMap<>();
//向集合添加元素
map.put(4,'rte');
map.put(23,'d234');
map.put(5,'e121');
map.put(75,'qee');
map.put(22,'fa');
//遍历
Set> entries = map.entrySet(); //获取到键值对集合
for (Map.Entry s:entries){
Integer key = s.getKey(); //获取到键值对对应的键
String value = s.getValue(); //获取到键值对对应的值
System.out.println(key+':'+value);
}
HashMap类概述
键是哈希表结构,可以保证键的唯一性
HashMap案例
上面两个跟Map集合中的案例一样,重点说下面的
首先封装一个学生类
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 int getAge() {
return age;
}
public void setName(String name) {
this.name = name;
}
public void setAge(int age) {
this.age = age;
}
@Override
public String toString() {
return 'Student{' +
'name='' + name + ''' +
', age=' + age +
'}';
}
}
在创建集合添加学生对象测试
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
public class HashMapTest1 {
public static void main(String[] args) {
//创建集合对象
HashMap hashMap = new HashMap<>();
//创建学生对象
Student s1 =new Student('student1',23);
Student s2 =new Student('student2',14);
Student s3 =new Student('student3',17);
Student s4 =new Student('student4',25);
Student s5 =new Student('student5',23);
//向集合添加元素
hashMap.put('sas',s1);
hashMap.put('qwe',s2);
hashMap.put('fsa',s3);
hashMap.put('ddd',s4);
hashMap.put('qca',s5);
//遍历
Set> entries = hashMap.entrySet();
for (Map.Entry s:entries){
String key = s.getKey();
Student value = s.getValue(); //也可以调用student中的get方法把名字,年龄获取出来遍历
System.out.println(key+':'+value);
}
}
}
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
public class HashMapTest2 {
public static void main(String[] args) {
//创建集合对象
HashMap hashMap = new HashMap<>();
//创建学生对象
Student s1=new Student('qa',23);
Student s2=new Student('ea',25);
Student s3=new Student('fa',22);
Student s4=new Student('da',15);
Student s5=new Student('qa',23);
//向集合添加元素
hashMap.put(s1,'111');
hashMap.put(s2,'222');
hashMap.put(s3,'333');
hashMap.put(s4,'444');
hashMap.put(s5,'555');
//遍历
Set> entries = hashMap.entrySet();
for (Map.Entry s:entries){
Student key = s.getKey();
String value = s.getValue();
System.out.println(key+':'+value);
}
}
}
从输出结果能发现,key有重复的对象,这违背了map中键是唯一的定义,原因是添加元素的put方法的源码涉及到hashCode方法和equals方法来判断元素是否重复,而我们创建做为key的自定义Student类中没有重写hashCode方法和equals方法,所以只能调用Object类中的equals方法来比较地址值,每一个学生对象都是new出来的,地址值固然不一样。
解决方法:在Student类中重写hashCode方法和equals方法
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
Student student = (Student) o;
return age == student.age && Objects.equals(name, student.name);
}
@Override
public int hashCode() {
return Objects.hash(name, age);
}
这样key就不会重复了
继承自HashMap类,实现了Map接口
Map接口的哈希表和链接列表实现,具有可预知的迭代顺序。
哈希表保证元素的唯保证key是唯一
链表保证有序
例:
import java.util.LinkedHashMap;
import java.util.Map;
import java.util.Set;
public class LinkedHashMapTest1 {
public static void main(String[] args) {
//创建集合对象
LinkedHashMap map = new LinkedHashMap<>();
//向集合添加元素
map.put('s1','qqw');
map.put('s2','q232');
map.put('s3','q211');
map.put('s4','d23');
map.put('s1','dsa');
//遍历
Set> entries = map.entrySet();
for (Map.Entry s:entries){
String key = s.getKey();
String value = s.getValue();
System.out.println(key+':'+value);
}
}
}
从结果可以看出重复的key的值被覆盖了,并且输出的顺序就是存放的顺序
TreeMap类概述
键是红黑树结构,可以保证键的排序和唯一性
TreeMap案例
import java.util.Map;
import java.util.Set;
import java.util.TreeMap;
public class TreeMapTest1 {
public static void main(String[] args) {
//创建集合对象
TreeMap map = new TreeMap<>();
//向集合添加元素
map.put('HashSet','Set接口');
map.put('TreeSet','Set接口');
map.put('LinkedHashSet','Set接口');
map.put('HashMap','Map接口');
map.put('HashMap','Map接口');
//遍历
Set> entries = map.entrySet();
for (Map.Entry s:entries){
String key = s.getKey();
String value = s.getValue();
System.out.println(key+':'+value);
}
}
}
可以看出结果去重了,而且按key中的首字母排序,因为无参构造走的是自然排序,String类实现了Comparable接口,重写了ComparaTo方法,String中ComparaTo方法比较ASCII码值,所以按首字母排序。
方法
首先封装一个学生类跟学生类1一样的
再创建集合
import java.util.Map;
import java.util.Set;
import java.util.TreeMap;
public class TreeMapTest2 {
public static void main(String[] args) {
//创建集合对象
TreeMap map = new TreeMap<>();
//创建学生对象
Student2 s1 =new Student2('student1',23);
Student2 s2 =new Student2('student2',22);
Student2 s3 =new Student2('student3',23);
Student2 s4 =new Student2('student1',23);
Student2 s5 =new Student2('student4',20);
//向集合添加元素
map.put(s1,'q111');
map.put(s2,'w111');
map.put(s3,'e111');
map.put(s4,'q111');
map.put(s5,'t111');
//遍历
Set> entries = map.entrySet();
for (Map.Entry s:entries){
Student2 key = s.getKey();
String value = s.getValue();
System.out.println(key+':'+value);
}
}
}
然后到这一步你会报错,因为这里走的还是无参构造,自然排序,所创建的Stuent2类没有实现Comparable接口,而自然排序这个接口中有一个向下转型,所以会类型转换异常报错
解决方法:创建的Student2类需实现Comparable接口,并重写接口的ComparaTo方法,在其中自定义排序方法
public class Student2 implements Comparable {
private String name;
private int age;
public Student2() {
}
public Student2(String name, int age) {
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public int getAge() {
return age;
}
public void setName(String name) {
this.name = name;
}
public void setAge(int age) {
this.age = age;
}
@Override
public String toString() {
return 'Student{' +
'name='' + name + ''' +
', age=' + age +
'}';
}
@Override
public int compareTo(Student2 o) {
//比较年龄是否一样
int i1=o.age-this.age;
//年龄一样,姓名不一定一样
int i2= i1==0 ? o.name.compareTo(this.name):i1;
return i2;
}
}
可以看出结果去重且按自定义方法排序
方法
如果你不想改动学生类,那就走有参构造方法,也就是比较器排序
Map集合练习案例
例'aababcabcdabcde',获取字符串中每一个字母出现的次数要求结果:abcde
import java.util.Map;
import java.util.Set;
import java.util.TreeMap;
public class MapTest4 {
public static void main(String[] args) {
//创建字符串对象
String s='aababcabcdabcde';
//创建集合对象
TreeMap map = new TreeMap<>();
char[] chars = s.toCharArray(); //转成字符数组
//遍历字符数组
for (Character c : chars) {
Integer integer = map.get(c); //用每一个字符当作键去找值
if (integer == null) { //如果输出值为null,表示集合中没有这个键,添加这个键并赋值1;
map.put(c, 1);
} else { //如果输出不为null,表示集合中有这个键,赋值返回的值value+1,返回覆盖到集合中
integer++;
map.put(c, integer);
}
}
//遍历集合
Set> entries = map.entrySet();
for (Map.Entry e:entries){
Character key = e.getKey();
Integer value = e.getValue();
System.out.print(key+'('+value+')');
}
}
}
例ArrayList集合嵌套HashMap集合
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
public class MapTest5 {
public static void main(String[] args) {
//创建ArrayList集合对象
ArrayList> list = new ArrayList<>();
//创建2个HashMap集合,并添加元素
HashMap map1 = new HashMap<>();
map1.put('user1','qwq');
map1.put('user2','q33q');
HashMap map2 = new HashMap<>();
map2.put('user3','q3we');
map2.put('user4','aa');
//把HashMap集合添加进入ArrayList集合
list.add(map1);
list.add(map2);
//遍历ArrayList集合
for (HashMap s:list){
//遍历HashMap集合
Set> entries = s.entrySet();
for (Map.Entry m:entries){
String key = m.getKey();
String value = m.getValue();
System.out.println(key+':'+value);
}
}
}
}
HashMap与Hashtable的区别
HashMap和Hashtable它们存储的都是一个个的键值对
HashMap中允许key,value为null,而Hashtable不允许
Hashtable是线程安全的,HashMap是不安全的
Collections类概述
针对集合操作的工具类
Collection是单列集合的顶层接口,有两大子类接口:List接口和Set接口
Collections是一个针对于集合操作的工具类,可以对集合进行排序,还有查找
Collections成员方法
publicstatic
import java.util.ArrayList;
import java.util.Collections;
public class CollectionsTest1 {
public static void main(String[] args) {
//创建集合对象
ArrayList list = new ArrayList<>();
//向集合添加元素
list.add(54);
list.add(23);
list.add(123);
list.add(42);
list.add(32);
list.add(24);
//public static void sort(List list) 排序
System.out.println('原集合:'+list);
Collections.sort(list);
System.out.println('排序后:'+list);
}
}
publicstatic
System.out.println('原集合:'+list);
int i = Collections.binarySearch(list, 123);
System.out.println(i);
publicstatic
System.out.println('原集合:'+list);
Collections.reverse(list);
System.out.println('反转后:'+list);
publicstaticvoidshuffle(List>list)随机置换
System.out.println('原集合:'+list);
Collections.shuffle(list);
System.out.println('随机置换后:'+list);
Collections中的方法能线程不安全的集合变成安全的
例:static
返回由指定列表支持的同步列表。
可以看出两个list和list1是一样的,Collections只是给list套了一层,让它变成安全的,在Vector类中说过虽然Vector是安全的,但Collections工具类比它更好。
文章为作者独立观点,不代表 股票程序化软件自动交易接口观点