java集合课程,I学霸官方免费课程三十三:Java集合框架之Map集合

I学霸官方免费教程三十三:Java集合框架之Map集合

Map接口

Map集合采用键值对(key-value)的方式存储数据,其中键不可以重复、值可以重复。

常用类有HashMap、TreeMap和Properties

HashMap类

假如,现在我有一个集合,集合中存储着一批WiFi的名称和密码,现在要求通过名称快速找到密码。这样的需求使用List集合实现起来非常困难,Java为我们提供了另一种形式的集合,可以很好的解决这样的问题。就是Map集合。实例:

package map.hashMap;

import java.util.HashMap;

import java.util.Map;

/**

* 演示HashSet

* @author 学霸联盟 - 赵灿

*/

public class HashMapDemo {

public static void main(String[] args) {

//创建集合对象

Map map = new HashMap();

/*

* 注意:map集合添加元素的方法是put,不是add

* 前一个参数代表key(键),后一个参数代表value(值)

*/

map.put("wifiName1", "password1");

/*

* 当出现key重复时,后面的值会将前面的值覆盖

* 而value重复时,无影响

*/

map.put("wifiName2", "password2");

map.put("wifiName2", "password3");

map.put("wifiName3", "password3");

//获取集合的长度,加入4次,长度为3

int size = map.size();

System.out.println(size);

//获取key为"wifiName2"的value

String wifi2 = (String)map.get("wifiName2");

System.out.println(wifi2);

//两种方式转换成String都可以

String wifi3 = map.get("wifiName3").toString();

System.out.println(wifi3);

}

}

运行结果:

3

password3

password3

注意:Set集合会将加入的元素存储在Map集合的key上,如果出现重复不会覆盖,保留前一个;但是Map集合中加入元素出现key相同的情况时,key不会覆盖,但是value会被后加入的value覆盖。

上面我们讲到向Set集合中添加元素时,会创建Node(节点),在节点的key中保持着当前加入的元素。在该节点中还有一个value属性,同样保存一个Object对象,只不过Set中没有使用这个value属性。而Map集合中需要存储两个值key和value,其中我们调用put方法时传入的第一个参数保存在Node对象的属性key上,传入的第二个参数就是保存在Node对象的属性value上。

由此一来,在使用key获取Map集合中对应的value时,先通过在hash表中找到key所在的Node对象,然后就返回Node对象中value的值,这样就得到了key所对应的value值了。

Map集合一些常用方法的演示实例:

package map.hashMap;

import java.util.Collection;

import java.util.HashMap;

import java.util.Set;

/**

* 演示HashMap类中的一些常用方法

* @author 学霸联盟 - 赵灿

*/

public class HashMapMethodDemo {

public static void main(String[] args) {

//创建两个班级class1和class2

HashMap class1 = new HashMap();

HashMap class2 = new HashMap();

/*

* 向两个班级中各添加三个学生和成绩

* 1班中有个叫“王五”的同学,成绩是50分

* 2班中也有个叫“王五”的同学,成绩是90分

*/

class1.put("张三", "80分");

class1.put("李四", "60分");

class1.put("王五", "50分");

class2.put("赵四", "80分");

class2.put("陈六", "0分");

class2.put("王五", "90分");

//判断1班有没有姓名叫“王五”的同学

boolean containsKey = class1.containsKey("王五");

System.out.println("集合class1中有没有key是王五:" + containsKey);

System.out.println("-------------------------------------");

//判断1班有没有成绩是90分的同学

boolean containsValue = class1.containsValue("90分");

System.out.println("集合class1中有没有value是90分:" + containsValue);

System.out.println("-------------------------------------");

//将2班同学合并到一班

class1.putAll(class2);

//获取班级人数(集合长度)

int size = class1.size();

System.out.println("合并后的班级总人数:" + size);

System.out.println("-------------------------------------");

//获取1班所有同学的姓名

Set nameSet = class1.keySet();

//增强for循环输出所有姓名

for (Object o : nameSet) {

System.out.print(o + " ");

}

System.out.println();

System.out.println("-------------------------------------");

//获取1班所有同学的成绩

Collection scores = class1.values();

//增强for循环输出所有成绩

for (Object o : scores) {

System.out.print(o + " ");

}

System.out.println();

System.out.println("-------------------------------------");

//获取1班所有同学的姓名和成绩

Set nameAndScoreSet = class1.entrySet();

//增强for循环输出所有成绩

for (Object o : nameAndScoreSet) {

System.out.print(o + " ");

}

System.out.println();

System.out.println("-------------------------------------");

//获取王五的成绩

Object wangwuScore = class1.get("王五");

System.out.println("合并后王五的成绩:" + wangwuScore);

System.out.println("-------------------------------------");

//删除key为“王五”的value

class1.remove("王五");

//删除“王五”后

System.out.println("王五的成绩:" + class1.get("王五"));

System.out.println("是否包含叫“王五”的key:" + class1.containsKey("王五"));

System.out.println("是否包含“90分”的value:" + class1.containsValue("90分"));

System.out.println("-------------------------------------");

//替换陈六的成绩

class1.replace("陈六", "59分");

System.out.println("替换后陈六的成绩:" + class1.get("陈六"));

System.out.println("-------------------------------------");

//清空集合

class1.clear();

//判断集合是否为空

System.out.println("用clear方法清除后集合是否为空:" + class1.isEmpty());

}

}

总结:

Map以键值对的结构存储;

key出现重复时,新加入的key不会覆盖原key,但新加入的value会覆盖原key对应的value

key和value都可以使用null

特殊说明:其实Set集合就是将元素存储到Map的键上。创建HashSet对象A时,会底层会创建一个HashMap的对象map,当想Set集合A中添加元素时(A.add("abc")),此时会调用map.put("abc", obj);

所以Set的实现方式就是Map中key的实现方式(数组 + 单项链表),由于元素存储数组的下标由特定的hash算法获得,所以也称为散列存储以下是HashSet中的源码

//创建HashSet对象是会在底层创建一个HashMap对象

public HashSet() {

map = new HashMap<>();

}

//向Set集合中添加元素时,底层是将添加的元素添加到map集合的key上

public boolean add(E e) {

return map.put(e, PRESENT)==null;

}

TreeMap类

由名称可知,其key和TreeSet一样;其他属性同HashMap。所以这里不再详细讲述。实例:

package map.treeMap;

import java.util.Set;

import java.util.TreeMap;

/**

* 演示TreeSet集合

* @author 学霸联盟 - 赵灿

*/

public class TreeMapDemo {

public static void main(String[] args) {

//创建三个树枝对象

Branch b1 = new Branch(10);

Branch b2 = new Branch(5);

Branch b3 = new Branch(8);

//创建TreeMap对象

TreeMap tm = new TreeMap();

tm.put(b1, "树枝10");

tm.put(b2, "树枝5");

tm.put(b3, "树枝8");

//获取TreeMap中包含所有的key的集合

Set ts = tm.keySet();

//循环输出key

for(Object o : ts){

Branch b = (Branch)o;

//输出年轮

System.out.print("年轮:" + b.getAnnualRing());

//根据有序的key,获取有序的value

System.out.println(" 对应的value:" + tm.get(b));

}

}

}

/**

* 树枝类Branch

* 加入TreeSet集合的元素类型必须实现Comparable接口

* 否则程序运行的时候会出现异常

* @author 学霸联盟 - 赵灿

*/

class Branch implements Comparable{

//年轮:用于排序的依据

private int annualRing;

//带参构造方法

public Branch(int annualRing){

this.annualRing = annualRing;

}

//重写接口中的方法

@Override

public int compareTo(Object o) {

//强制类型转换

Branch b = (Branch)o;

/*

* 使用年轮作为排序比较的依据

* 当前对象年轮减去参数传入的Branch对象的年龄

* 结果等于0表示:两个树枝年轮相等,排序不分先后

* 结果大于0表示:当前对象的年轮大,排在后面

* 结果小于0表示:参数对象的年轮大,排在后面

*/

int result = this.annualRing - b.annualRing;

return result;

}

//获取年轮

public int getAnnualRing(){

return annualRing;

}

}

运行结果

年轮:5 对应的value:树枝5

年轮:8 对应的value:树枝8

年轮:10 对应的value:树枝10

Properties类

从文件中获取键值对

文件内容格式

key = value实例:

文件名:properties.txt

文件内容:

username = admin

password = 123456

文件地址:src/map/properties/properties.txt

其中文件地址是从项目根目录开始的

实例:

package map.properties;

import java.io.FileInputStream;

import java.util.Properties;

/**

* 演示Properties类中的一些常用方法

* @author 学霸联盟 - 赵灿

*/

public class PropertiesDemo {

public static void main(String[] args) {

//创建Properties对象

Properties p = new Properties();

/*

* 以下代码暂时先知道是什么作用即可,后面会讲解

* try - catch语句的作用是捕获异常

* load方法的作用是加载文件

* 其中的参数是文件的地址

*/

try {

p.load(new FileInputStream("src/map/properties/properties.txt"));

} catch (Exception e) {

System.out.println("加载出错");

}

//获取文件中username对应的值

String username = p.getProperty("username");

System.out.println("用户名:" + username);

//获取文件中password对应的值

String password = p.getProperty("password");

System.out.println("密码:" + password);

}

}

运行结果:

用户名:admin

密码:123456

版权声明:本文为博主原创文章,未经博主允许不得转载。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值