Properties没有被注意的地方
SRE实战 互联网时代守护先锋,助力企业售后服务体系运筹帷幄!一键直达领取阿里云限量特价优惠。
源起:
今天阅读源码时发现一个地方不理解:
为什么以下代码第10行 get() 之后value为null时还去 getProperty() 呢?
org.springframework.util.CollectionUtils
1 public static <K, V> void mergePropertiesIntoMap(Properties props, Map<K, V> map) { 2 if (map == null) { 3 throw new IllegalArgumentException("Map must not be null"); 4 } else { 5 String key; 6 Object value; 7 if (props != null) { 8 for(Enumeration en = props.propertyNames(); en.hasMoreElements(); map.put(key, value)) { 9 key = (String)en.nextElement(); 10 value = props.get(key); 11 if (value == null) { 12 value = props.getProperty(key); 13 } 14 } 15 } 16 17 } 18 }
跟进去发现Properties类除了继承HashTable用于存储<K, V>数据之外,自身还持有一个
protected Properties defaults;
因此就相当于可以无限嵌套了吧。。。
测试:
Properties有些需要避坑的地方稍微整理了下:
1 @Test 2 public void javaCoreProperties () { 3 // public class Properties extends Hashtable<Object,Object> 4 5 // 初始化时传入的作为default属性(Properties类型)存储 6 Properties props = new Properties(System.getProperties()); 7 // 调用内部put方法,与put仅形参类型不同 8 props.setProperty("base.date", "2019-05-09"); 9 // 相比于setProperty适用范围更广,它的形参都是Object类型 10 props.put("base.time", "14:15:00"); 11 props.put("base.object", new Date()); 12 13 System.out.println(props.get("base.date")); 14 System.out.println(props.getProperty("base.date")); 15 16 System.out.println(props.get("base.time")); 17 System.out.println(props.getProperty("base.time")); 18 19 // get与getProperty不等价 20 // get仅获取put进去的存储在父类HashTable中的数据 21 System.out.println(props.get("java.runtime.version")); 22 // getProperty会优先在查找父类HashTable中的数据,如果没有再到自己拥有的default中查找;查找方法依然是跟这里相同 23 System.out.println(props.getProperty("java.runtime.version")); 24 25 // 可以获取对象 26 System.out.println(props.get("base.object")); 27 // 获取到Value对象,判断发现不是String类型,再去default中找,依然找不到,返回null 28 System.out.println(props.getProperty("base.object")); 29 30 31 // Key和Value不能为空,否则抛出NPE,这是HashTable决定的,HashMap就没有这个限制 32 //props.put(new Object(), null); // 有校验 33 //props.put(null, 123); //计算Key的hashCode时引发 34 35 // 这个会引起java.lang.ClassCastException,因为list遍历时,会将Key和Value强制转化为String 36 //props.put(new Object(), 123); 37 props.put("007", "123"); 38 props.remove("base.object"); 39 40 props.list(System.out); 41 }
运行输出:
2019-05-09 2019-05-09 14:15:00 14:15:00 null 1.8.0_144-b01 Thu May 09 15:09:02 CST 2019 null -- listing properties -- base.time=14:15:00 java.runtime.name=Java(TM) SE Runtime Environment sun.boot.library.path=C:\DevBaseFiles\Java\jdk1.8.0_144\jre... java.vm.version=25.144-b01 base.date=2019-05-09 java.vm.vendor=Oracle Corporation
...
欢迎提出意见或建议,共同进步。

更多精彩