Java 编程之集合Map介绍和使用
Java 集合Map
1、Map集合介绍
1.1、Map集合的特点
打开API查询Map的描述。将键映射到值的对象。一个映射不能包含重复的键;每个键最多只能映射到一个值
。
阅读完Map集合的介绍之后发现,原来Map集合就是用来存放具有对应关系的数据的。即就是key对应value这样的关系,并且要求key不能重复。
public class MapDemo { public static void main(String[] args) { //创建Map对象 Map<String, String> map = new HashMap<String,String>(); //给map中添加元素 map.put("星期一", "Monday"); map.put("星期日", "Sunday"); //当给Map中添加元素,会返回key对应的原来的value值,若key没有对象的值,返回null System.out.println(map.put("星期一", "Mon")); //根据指定的key获取对应的value String en = map.get("星期日"); System.out.println(en); //根据key删除元素,会返回key对应的value值 String value = map.remove("星期日"); System.out.println(value); } }
1.2、keySet 方法演示
如何获取Map中的所有key呢?由于Map中的所有key都是不重复的,所以获取到Map中的所有key应该会存放在Set集合中。那么查询Map的API发现,有个方法keySet。
public class MapDemo { public static void main(String[] args) { //创建Map对象 Map<String, String> map = new HashMap<String,String>(); //给map中添加元素 map.put("星期一", "Monday"); map.put("星期日", "Sunday"); //获取Map中的所有key Set<String> keySet = map.keySet(); //遍历存放所有key的Set集合 Iterator<String> it =keySet.iterator(); while(it.hasNext()){ //得到每一个key String key = it.next(); //通过key获取对应的value String value = map.get(key); System.out.println(key+"="+value); } } }
1.3、entrySet 方法演示
继续查阅Map的API,发现还有一个方法是entrySet,这个方法的描述是得到所有key和value的映射关系,这是啥意思呢?假设Map中存放一对一对的夫妻,那么entrySet获取到是每一对夫妻这种夫妻关系。
public class MapDemo { public static void main(String[] args) { //创建Map对象 Map<String, String> map = new HashMap<String,String>(); //给map中添加元素 map.put("星期一", "Monday"); map.put("星期日", "Sunday"); //获取Map中的所有key与value的对应关系 Set<Entry<String,String>> entrySet = map.entrySet(); //遍历Set集合 Iterator<Entry<String,String>> it =entrySet.iterator(); while(it.hasNext()){ //得到每一对对应关系 Entry<String,String> entry = it.next(); //通过每一对对应关系获取对应的key String key = entry.getKey(); //通过每一对对应关系获取对应的value String value = entry.getValue(); System.out.println(key+"="+value); } } }
注意:Map集合不能直接使用迭代器或者foreach进行遍历。但是转成Set之后就可以使用了。
2、Map集合常用子类介绍
在讲解Collection集合时,给大家讲解查看API的技巧,所以在学习Map的子类时,就结合前面讲解的特点来分析Map的子类即可。
2.1、Map常见子类的特点
Map有多个子类,这里我们主要讲解常用的HashMap和TreeMap集合。
HashTable:数据结构-哈希表
。是同步的,不允许null作为键和值。被hashMap替代。
Properties:属性集,键和值都是字符串,而且可以结合流进行键值的操作。等到了IO流,你会更清楚。
HashMap:数据结构-哈希表
。不是同步的,允许null作为键和值。HashMap下有个子类LinkedHashMap基于链表+哈希表。可以保证map集合有序(存入和取出的顺序一致)。
TreeMap:数据结构-二叉树
。不是同步的。可以对map集合中的键进行排序。
2.2、HashMap存储自定义键值
练习一:学生对象(姓名,年龄)都有自己的归属地,既然有对应关系。将学生对象和归属地存储到map集合中。注意:同姓名同年龄视为重复的键。
public class HashMapTest { public static void main(String[] args) { //1,创建hashmap集合对象。 Map<Student,String> map = new HashMap<Student,String>(); //2,添加元素。 map.put(new Student("lisi",28), "上海"); map.put(new Student("wangwu",22), "北京"); map.put(new Student("zhaoliu",24), "成都"); map.put(new Student("zhouqi",25), "广州"); map.put(new Student("wangwu",22), "南京"); //3,取出元素。keySet entrySet // Set<Student> keySet = map.keySet(); // for(Student key : keySet){} for(Student key : map.keySet()){ String value = map.get(key); System.out.println(key.toString()+"....."+value); } } }
注意:当给HashMap中存放自定义对象时,如果自定义对象作为key存在,这时要保证对象唯一,必须复写对象的hashCode和equals方法(如果忘记,请回顾HashSet存放自定义对象)。
如果要保证map中存放的key和取出的顺序一致,可以使用LinkedHashMap
集合来存放。
2.3、TreeMap存储自定义键值
练习二: 学生对象(姓名,年龄)都有自己的归属地,既然有对应关系。 将学生对象和归属地存储到map集合中。
注意:同姓名同年龄视为重复的键。 按照学生的年龄进行从小到大的排序。 TreeMap。
public class TreeMapTest { public static void main(String[] args) { // 1,创建TreeMap集合对象。 Map<Student, String> map = new TreeMap<Student, String>(); // 2,添加元素。 map.put(new Student("lisi", 28), "上海"); map.put(new Student("wangwu", 22), "北京"); map.put(new Student("zhaoliu", 24), "成都"); map.put(new Student("zhouqi", 25), "广州"); map.put(new Student("wangwu", 22), "南京"); //3,取出所有元素,entrySet() for(Map.Entry<Student, String> me : map.entrySet()){ Student key = me.getKey(); String value = me.getValue(); System.out.println(key+"::"+value); } } }
注意:给TreeMap存放自定义对象,自定义对象作为key进行排序时,自定义对象必须具备比较功能,即实现Comparable接口。
如果需要特定方式进行比较,我们也可以给TreeMap集合传递自定义的比较器进行比较。
2.4、Map练习-字母出现次数
练习:
“werertrtyuifgkiryuiop”,获取字符串中每一个字母出现的次数。要求返回结果个格式是 a(1)b(2)d(4)…;
思路:
1,获取到字符串中的每一个字母。
2,用字母取查表,如果查到了该字母对应的次数,就将这个次数+1后重新存回表中。
如果没有查到呢?将该字母和1存到表中。
3,每一字母都查完表后,表中记录的就是所有字母出现的次数。
字母和次数之间存在对应关系,而且字母是唯一性的,所以可以使用map集合做表进行查询。通过结果发现 字母有顺序的,所以可以通过map集合中的treemap作为表。
public class MapTest { public static void main(String[] args) { String str = "awaa+acr=ebarct,btydui[efgkiryuiop"; str = getCharCount(str); System.out.println(str); } /*
* 获取字符串中的字母出现次数。
*/ public static String getCharCount(String str) { //1,将字符串转成字符数组。 char[] chs = str.toCharArray(); //2,定义表。treemap. TreeMap<Character, Integer> map = new TreeMap<Character, Integer>(); //3,遍历字符数组。 for (int i = 0; i < chs.length; i++) { //判断必须是字母。 if(!(chs[i]>='a' && chs[i]<='z' || chs[i]>='A' && chs[i]<='Z')){ continue; } //4,将遍历到的字母作为键去查map这个表。获取对应的次数。 Integer value = map.get(chs[i]); //5,有可能要查询的字母在表中不存在对应的次数,需要判断。 //如果返回是null,说明字母没有对应的次数。就将这个字母和1存储到表中。 if(value == null){ //将字母和1存储。 map.put(chs[i],1); }else{ //否则,说明有对应的次数对次数自增。将字母和新的次数存储到表中。 value++; map.put(chs[i],value); } } return mapToString(map); } /*
* 将map集合中的键值转成 格式是 a(1)b(2)d(4)......
* map中有很多数据,无论是多少个,什么类型,最终都变成字符串。
* StringBuffer 这个容器就符合这个需求。如果是单线程,建议使用StringBuilder。
*
*/ private static String mapToString(Map<Character, Integer> map) { //1,明确容器。 StringBuilder sb = new StringBuilder(); //2,遍历map集合。 for(Character key : map.keySet()){ Integer value = map.get(key); sb.append(key+"("+value+")"); } return sb.toString(); } }
本文地址:https://blog.csdn.net/m0_49297152/article/details/108231972
上一篇: Java面向对象思想理解总结
下一篇: 基本排序看这篇就够了