6.1~4查找之顺序、二分、散列表

6.1顺序查找

顺序查找

int seq_search(Table T,Elem key){//顺序没有可从前往后,从后往前
   for(int i=0;key!=T[i];i++) //顺序结构的Table;可链式结构
   return i;
}

平均查找长度

对于n个单元的表,给定key与表中第i个关键字相等,需比较i次;

ASL_success=1/n*(1+2+…+n)=n+1/2;

优点:对数据元素存储的方式没要求,顺序或链式存储结构;对表中数据可以为无序;

缺点:当n较大时,平均查找长度较大,效率低;

注:链表只能顺序查找

6.2折半查找

折半查找&二分查找,只用于已排序序列。

int binary_search(SeqTable T,Elem key){
    int low=0,high=T.len-1,mid;
    while(low < high){
        mid = (low+high)/2; //向下取整
        if(T[mid]<key) low=mid+1;
        else if(T[mid]>key) high=mid-1;
        else return mid;
    }
}

折半查找的时间复杂度为O(log_2{n}),平均情况比顺序查找效率高;

平均查找长度:ASL=1/n(1x1+2x2+…+hx2^h-1)

平均查找成功长度和平均查找失败长度(⭐️)

会画折半查找的判定树,王道p243.

n个元素的有序表,的判定树的高度向上取整log_2{n+1}

注:二分查找的存储结构必须具有随机存取的特性,故只用于线性表的顺序存储结构,即只用于顺序表,不适合链表。且要求有序,小到大,或大到小影响算法的mid移动。

6.3分块查找(不考)

分块查找又称索引顺序查找,集合了顺序查找和折半查找,将表分块,索引表顺序存储块中最大或最小关键字,将块有序排列;

分块查找先在索引表折半查找找到指定块,再在块中顺序查找指定关键字;

6.4 散列表(HashTable)

注:一篇博文,散列表的概念和实现,链接:https://blog.csdn.net/lin1094201572/article/details/89111958

散列表的查找的效率取决于比较的次数;

散列表中散列函数为核心,用于将关键字映射到对应地址的函数,Hash(key)=address;

那么问题来了,若两个或以上关键字映射到相同地址呢,这种问题叫做冲突,冲突的关键字为同义词冲突不可避免,故我们需要解决冲突;

解决冲突的办法有:开放地址法、拉链法;

1.Hash函数的构造

散列函数应满足1)包含所有关键字;2)地址等概率、均匀分布;3)简单,计算快;

常用散列函数:

1.直接定址法:H(key)=a*key+b;不会造成冲突,但造成存储空间浪费;

2.除留余数法:H(key)=key%p;p小于表长;

3.数字分析法;4.平方取中法;5.折叠法;

2.处理冲突的方法

1.开放地址

1)线性探测法;2)平方探测法;3)再散列法;

2.拉链法

采用线性链表存储所有关键字,每一链表由一地址标识;适用于经常插入和删除的情况;

3.散列表查找及性能分析

决定散列表的查找效率的因素:散列函数处理冲突的方法装填因子

装填因子:a=表中记录数/表长;

散列表的平均查找长度依赖于装填因子;还会受到堆积(聚集)现象的影响

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章