EnumMap的实现原理

先看看EnumMap的构造方法之一:

//类型
private final Class<K> keyType;
 
//所有key值的数组
private transient K[] keyUniverse;
//key对应的value值,长度固定为枚举个数
private transient Object[] vals;

public EnumMap(Class<K> keyType) {
        //把类型参数赋值给keyType
        this.keyType = keyType;
        //这段代码底层用到了values的方法,把枚举类的key值都全部取出来,放到keyUniverse数组里
        keyUniverse = getKeyUniverse(keyType);
        //构造长度为keyUniverse数组长度的vals数组,用来存放值
        vals = new Object[keyUniverse.length];
    }

EnumMap的put方法:

  public V put(K key, V value) {
        //检查key的类型是不是对的,不符合则抛出异常
        typeCheck(key);
        //拿下标,对应的就是枚举成员在枚举中的顺序位置
        int index = key.ordinal();
        //先取得这个下标原来的值
        Object oldValue = vals[index];
        //做一个对于null值的特殊处理
        vals[index] = maskNull(value);
        //如果原来下标是null,现在赋值上去了,size就会加1,size代表这数组里的实际元素有多少
        if (oldValue == null)
            size++;
        //对NULL对象做处理,返回    
        return unmaskNull(oldValue);
    }
    
//为了判断value到底是不是null,如果真是null就赋值为NULL对象
private Object maskNull(Object value) {
        return (value == null ? NULL : value);
    }
    
//返回的时候用,如果真是NULL,那么就给它再转回成null做返回值    
private V unmaskNull(Object value) {
        return (V)(value == NULL ? null : value);
    }
    
//NULL其实就是个重写了hashCode方法和toString方法的Object类
private static final Object NULL = new Object() {
        public int hashCode() {
            return 0;
        }

        public String toString() {
            return "java.util.EnumMap.NULL";
        }
    };

EnumMap的get方法:

public V get(Object key) {
        //先校验key是否合法,合法则直接通过key对应的下标在vals数组里取值,不然就返回null
        return (isValidKey(key) ?
                unmaskNull(vals[((Enum<?>)key).ordinal()]) : null);
    }

总结

通过以上方法可以看出,EnumMap有两个数组属性很关键,一个 K[ ] keyUniverse数组用来初始化时放入枚举的所有key值,一个Object[] vals数组用来存放value值,他们是通过下标来一一对应的,因为put的时候会先取key的下标,来作为Object[] vals数组的下标,然后赋值,get时就能够直接通过key的下标在Object[] vals数组里找到对应的value值。当然了,用来作为类型检查的Class keyType 属性也是很关键的,他决定了这个EnumMap究竟能操作哪个枚举,要是不对应,就会抛出异常。

发布了178 篇原创文章 · 获赞 180 · 访问量 3万+

猜你喜欢

转载自blog.csdn.net/weixin_38106322/article/details/104292701