zoukankan      html  css  js  c++  java
  • iOS 字典实现原理

    在目前的开发中,NSDictionary是经常被使用,不过很少人会研究字典NSDictionary底层的实现,下面我们来一起看一下NSDictionary的实现原理。

    一、字典原理

    字典通过使用- (void)setObject:(id)anObject forKey:(id)aKey;方法,用Hash表来实现key和value之间映射和存储的。

    二、哈希原理

    哈希概念:哈希表本质是一个数组,每一个元素称为一个箱子,而箱子里面的存放的是键值对。

    哈希表(Hash Table)也叫做散列表,这是根据关键码(key vlaue)而直接进行访问的数据结构。换句话说,通过把关键码映射到表里面的一个位置来访问记录,用来加快查找的速度。映射的函数就叫做散列函数,存放记录的数组也叫做散列表。

    给定表M(称为哈希表),存在函数f(key)(函数称为哈希函数),给定任意的key值,然后代入函数之后能得到包含改关键字的记录在表中的具体位置。

    三、哈希存储过程

    3.1 首先根据key计算出它的哈希值h

    3.2 如果箱子的个数为n,那么key值是应该放在第(h%n)个箱子中

    3.3 如果该箱子已经有了值,就使用开放寻址法或者拉链法进行解决冲突。

    如果我们在使用拉链法解决哈希冲突时候,每个箱子都是一个链表,属于同一个箱子的所有键值都会排列在链表中。

    》〉》拓展

    哈希表有一个比较重要的属性:负载因子(load factor):是用来衡量哈希表的空/满程度,公式如下:

    负载因子 = 总键值对数 / 箱子个数

    如果负载因子越大,意味着哈希表越满,也就越容易导致冲突,性能也就是越低。在日常开发中,当负载因子大于某个常数(1或者0.75)时,哈希表就会自动扩展。

    哈希表的扩容虽然可以解决部分问题,但并不总是有效的解决负载因子过大的问题。假如所有的哈希值都一样,即使扩容之后,位置也不会发生改变,虽然负载因子降低,但不能提高哈希表的查找性能。

    综上:发现哈希表有两个问题:

    1.如果哈希表中箱子键值本来就很多,仅仅扩容移动数据,性能影响较大。

    2. 如果哈希函数设计不是很合理,那么在极端的情况下会变成线性表,性能非常低

  • 相关阅读:
    Linux进阶之Linux中的标准输入输出
    PermCheck
    FrogRiverOne
    PermMissingElem
    FrogJmp
    TapeEquilibrium
    恒生电子长沙2016实习生笔试题
    接口和抽象类的异同点?
    C#实现二叉树
    C#实现栈和队列
  • 原文地址:https://www.cnblogs.com/guohai-stronger/p/9475064.html
Copyright © 2011-2022 走看看