`

java需要关注的知识点---HashMap

阅读更多

做了两年的java,感觉技术上没多大提升,特别是呆了一年外企,整理感觉自己都萎靡,不爱学习!
所以,写个帖子记下在网上看到的东西以及自己要去学习的内容!
努力奋斗!
1.HashMap的实现--------------------<在看>
   1.1 HashMap 的默认size是16,默认临界值是 12,默认的基数0.75。
   1.2 HashMap 的最大size是1<<30
   1.3 HashMap 中 transfer方法理解:

        
   
        void transfer(Entry[] newTable) {
        Entry[] src = table;
        int newCapacity = newTable.length;
        for (int j = 0; j < src.length; j++) {
            Entry<K,V> e = src[j];//标记1
            if (e != null) {
                src[j] = null;//标记2
                do {
                    Entry<K,V> next = e.next;//标记3
                    int i = indexFor(e.hash, newCapacity);//标记4
                    e.next = newTable[i];//标记5
                    newTable[i] = e;//标记6
                    e = next;//标记7
                } while (e != null);
            }
        }
    }


    标记1:从Entry 数组中获取到 oldTable中需要往newTable 插入的entry实例e。
    标记2:回收oldTable的内存。
    标记3:使用临时变量存储e.next的值,以便下次获取链表的下个需要遍历的值,直到e.next的值为空。
    标记4:根据e的hash值和新表中的容量计算e需要放置在新数组中的index值。
    标记5:把新数组index位置的值传递给e.next.
    标记6:把e放置在新数组index的位置下。
    标记7:重新设置e的值,把老数组e的next值传递给e.继续下一轮循环,直到e的next为空。


   1.4 HashMap 中 put 方法:

  
 public V put(K key, V value) {
        if (key == null)
            return putForNullKey(value);
        //根据hash算法获取需要插入数据的hash值
        int hash = hash(key.hashCode());
        //根据hash值,计算将要插入数组的index值
        int i = indexFor(hash, table.length);
        //如果该index下,存在链表值,遍历该链表,对比
        //链表中的每一个entry的实例的hash值和key
        //是否和需要插入的key和key的hash值相同。
        //如果相同:跟新原entry下的value;保持key,index和hash值不
        //变。
        //如果不相同:把新纪录插入到数组中。
        for (Entry<K,V> e = table[i]; e != null; e = e.next) {
            Object k;
            if (e.hash == hash && ((k = e.key) == key || key.equals(k))) {
                V oldValue = e.value;
                e.value = value;
                e.recordAccess(this);
                return oldValue;
            }
        }

        modCount++;
        addEntry(hash, key, value, i);
        return null;
    }
   


   1.5 HashMap中的addEntry方法:

   void addEntry(int hash, K key, V value, int bucketIndex) {
	Entry<K,V> e = table[bucketIndex];
        table[bucketIndex] = new Entry<K,V>(hash, key, value, e);
        //如果数组table的长度大于临界值,将table进行扩容,长度为原来的
        //两倍。
        if (size++ >= threshold)
            resize(2 * table.length);
    }


    1.6 HashMap中的静态内部类Entry:

 static class Entry<K,V> implements Map.Entry<K,V> {
        final K key;
        V value;
        Entry<K,V> next;
        final int hash;

        /**
         * h:新创建的entry实例的hash值。
         * k:键值
         * v:值
         * n:链表中但前entry实例的下一个entry的值。
         */
        Entry(int h, K k, V v, Entry<K,V> n) {
            value = v;
            next = n;
            key = k;
            hash = h;
        }

        public final K getKey() {
            return key;
        }

        public final V getValue() {
            return value;
        }

        public final V setValue(V newValue) {
	    V oldValue = value;
            value = newValue;
            return oldValue;
        }

        public final boolean equals(Object o) {
            if (!(o instanceof Map.Entry))
                return false;
            Map.Entry e = (Map.Entry)o;
            Object k1 = getKey();
            Object k2 = e.getKey();
            if (k1 == k2 || (k1 != null && k1.equals(k2))) {
                Object v1 = getValue();
                Object v2 = e.getValue();
                if (v1 == v2 || (v1 != null && v1.equals(v2)))
                    return true;
            }
            return false;
        }

        public final int hashCode() {
            return (key==null   ? 0 : key.hashCode()) ^
                   (value==null ? 0 : value.hashCode());
        }

        public final String toString() {
            return getKey() + "=" + getValue();
        }

  
        void recordAccess(HashMap<K,V> m) {
        }

        void recordRemoval(HashMap<K,V> m) {
        }
    }


    1.7 HashMap中的remove()方法:

final Entry<K,V> removeEntryForKey(Object key) {
        //获取hash值,如果key是null,hash值为0.
        int hash = (key == null) ? 0 : hash(key.hashCode());
        //获取该key的下标值。
        int i = indexFor(hash, table.length);

        Entry<K,V> prev = table[i];
        Entry<K,V> e = prev;

        while (e != null) {
            Entry<K,V> next = e.next;
            Object k;
            if (e.hash == hash &&
                ((k = e.key) == key || (key != null && key.equals(k)))) {
                modCount++;
                size--;
                if (prev == e)
                  //移动数组,用需要删除数组后一位置的值覆盖当前位置
                    table[i] = next;
                else      
                 //把需要删除的值,用当前链表中的下一个值
                //进行覆盖,依次用下一个覆盖上一个,直到
                //需要删除纪录后的每一数据都向前移动一位。
                    prev.next = next;
                e.recordRemoval(this);
                return e;
            }
            prev = e;
            e = next;
        }

        return e;
    }


有代码可得知:hashmap的删除不知是单单的把需要删除的纪录内存释放(设置为null)。而是
移动需要删除纪录后的每一个元素来覆盖前元素,释放最后一个值。
    1.8 HashMap 中的get()方法:

   public V get(Object key) {
        if (key == null)
            return getForNullKey();
        int hash = hash(key.hashCode());
        for (Entry<K,V> e = table[indexFor(hash, table.length)];
             e != null;
             e = e.next) {
            Object k;
            if (e.hash == hash && ((k = e.key) == key || key.equals(k)))
                return e.value;
        }
        return null;
    }


从上面代码可以得知,当key为空的时候,hashmap从table[0]的位置获取专门存取null键的位置获取值,key不为空的时候,根据传入key的hash值,获取index值(数组下标),然后 遍历该index下的entry链表,比对该hash值下所有的key,如果有key和传入的key相同,
获取该key下的value.
    1.9 HashMap的结构图(见附件)
[img]

 [/img]

 

  • 大小: 16.1 KB
分享到:
评论
1 楼 xiaguangme 2012-12-28  
写的很不错

相关推荐

    java需要关注的知识点---好的书本

    "java需要关注的知识点---好的书本"这一主题暗示了我们需要关注那些能帮助我们深入理解Java语言的资源。其中,标签"源码"和"工具"提醒我们不仅要关注理论,还要关注实际应用和开发工具。 首先,学习Java源码是理解...

    java基础教程----精华版

    下面将详细介绍Java语言的核心概念和关键知识点。 1. **Java语法基础**: - **变量**:在Java中,变量是存储数据的容器,分为基本类型(如int, double, boolean等)和引用类型(如类、接口、数组)。 - **数据...

    中信java培训资料------第一部分

    【归纳总结shi.doc】可能是对一段时间内学习内容的提炼,包含了关键知识点的梳理,比如类与对象的区别、封装、继承和多态性这面向对象的三大特性,以及异常处理机制和Java内存管理的基本原理,如垃圾回收机制。...

    HashMap知识点整理

    HashMap知识点整理,分条列点,详述hashmap的实现原理

    Java综合性实验----------

    这个实验涵盖了从基础到高级的多个Java知识点,旨在提升对Java语言的理解和应用能力。 首先,让我们关注"JavaCodeAnalyzer.jar"这个文件。这很可能是一个用于分析Java源代码的工具或者库。Java代码分析器通常用于...

    java提高篇(二三)-----HashMap.pdf

    以下是HashMap的一些关键知识点: 1. **HashMap的定义与实现**: HashMap实现了Map接口,继承自AbstractMap类。Map接口定义了键值对的存储规则,而AbstractMap提供了一个基础的Map接口实现,简化了自定义Map实现的...

    Java HashMap类详解

    本资源详细介绍了 Java 中的 HashMap 类,包括其实现机制、Hash 存储机制、集合存储机制等方面的知识点。 1. HashMap 和 HashSet 的关系 HashMap 和 HashSet 是 Java Collection Framework 的两个重要成员,虽然...

    java综合知识点总结-必背.zip

    这份“java综合知识点总结-必背.zip”文件很可能是为了帮助Java学习者或开发者整理和回顾核心概念,以便深入理解和应用。以下是根据标题和描述可能包含的一些关键知识点的详细解释: 1. **基础语法**: - 变量:...

    java HashMap原理分析

    知识点: 1. 哈希函数的原理和应用 2. HashMap的存储原理和查询效率 3. collisions处理和哈希碰撞问题 4. equals方法和hashCode方法的关系 5. Java中HashMap的应用和实现 详细解释: 1. 哈希函数的原理和应用 ...

    48-Java知识点 手写HashMap1

    本文将深入解析HashMap中的putVal()方法及其关键知识点。 首先,putVal()方法接受五个参数,其中最重要的两个是`hash`和`onlyIfAbsent`。`hash`是通过键(key)的hashCode值计算得到的,用于确定键值对在HashMap数组...

    Java 实例 - HashMap遍历源代码-详细教程.zip

    在Java编程语言中,HashMap是集合框架中一个重要...这个详细教程将涵盖以上所有知识点,通过源代码分析加深理解,帮助开发者熟练掌握HashMap的使用和遍历技巧。学习这些内容对于开发高效、可靠的Java应用程序至关重要。

    java面试java-interview-guide-master.zip

    这份"java面试java_interview_guide-master.zip"资源显然是为准备Java面试而设计的,包含了丰富的Java技术知识点和面试常见问题。以下将从Java语言基础、核心特性、集合框架、多线程、网络编程、异常处理、JVM内存...

    Java面试题大全--new

    以下是根据标题和描述推测的一些可能涵盖的Java知识点: 1. **基础概念** - Java的历史和发展:了解Java的起源、主要版本以及其在软件开发中的应用。 - Java的特点:讨论Java的跨平台性、自动内存管理、面向对象...

    js 版 java hashmap

    下面我们将详细探讨JavaScript中如何实现类似Java HashMap的功能,以及这个实现可能包含的关键知识点。 1. **哈希函数**:哈希函数是HashMap的核心,它负责将键转换为数组索引。一个优秀的哈希函数应尽量减少键的...

    java 的试题------

    Java是一种广泛使用的面向对象的编程语言,以其跨平台、高性能和丰富的类库而...以上知识点构成了Java程序员应掌握的基本技能,无论是初学者还是经验丰富的开发者,都需要不断地学习和实践以提升自己的Java技术水平。

    于笑扬java综合知识点总结-必背.doc

    ### 于笑扬Java综合知识点总结 #### 一、JDK常用的包 1. **java.lang**:包含运行Java程序所需的基本类,如`String`、`Math`等。 2. **java.util**:提供了集合框架(如`List`、`Map`)、日期和时间操作工具等。 3...

    learning-java-introduction-real-world-programming-5th.rar

    该书详细介绍了Java语言的基础知识以及如何将其应用于实际开发场景。第五版更新了最新的Java技术,确保读者能够掌握当前版本的Java编程技能。 Java是一种广泛应用的面向对象的编程语言,由Sun Microsystems(现为...

    JAVA 编程 API基础 JAVA开发平台,JAVA编程资源----JAVA API.zip

    在这里,我们可以讨论几个关键的Java API知识点: 1. **Java核心类库**:Java API的核心类库包括`java.lang`、`java.util`、`java.io`、`java.net`等。`java.lang`是最基本的包,包含所有Java程序都会用到的类,如`...

    【Java核心知识面试】-阿里Java面试集锦.zip

    这份面试集锦全面地覆盖了Java开发中的关键知识点,不仅适合准备面试的开发者,也适用于希望巩固和提升自身Java技能的在职工程师。通过深入学习和理解这些内容,将有助于在实际工作中更好地解决问题和优化代码。

    Javanotes7-web-site

    在《Javanotes7-web-site》中,读者将学习到以下关键知识点: 1. **Java基础语法**:包括数据类型(如整型、浮点型、字符型和布尔型)、变量声明、运算符、控制结构(如条件语句和循环)、数组和字符串的使用。 2....

Global site tag (gtag.js) - Google Analytics