查找
1.顺序查找
(1)适用于顺序表,链表。
(2)方法:在某个数据集合中,从第一个数据元素开始,依次向后查找。
i>顺序表的实现
int search (int a[],int n,int key)
{
int i,flag=1;
for(i=0;i<n;i++)
{
if(a[j]==key)
break;
}
if(flag==1)return -1;
else return i;
}
总结:平均查找长度为(1+n)/2;但是不适合大数据存储。
2.二分查找
(1)必须是经过排序的数据集合。
(2)只适用于顺序存储的数据集合。(即链表不能用二分查找)。
非递归实现:
int halfsearch(int d[],int low,int high,int key)
{
int mid;
while(low <=high)
{
mid=(low +high)/2;
if(d[mid]==key) return mid;
else if (d[mid]>key) high=mid-1;
else low=mid+1;
}
if (low>key) return -1;
}
递归实现:
int halfsearch(int d[],int low,int high,int key)
{
int mid;
if(low>high) return -1;
else{
mid=(low +high)/2;
if(d[mid]==key) return mid;
else if (d[mid]>key)
return halfsearch (d[],low, mid-1,key);
else return halfsearch(d[],mid+1,high,key);
}
}
总结:时间复杂度O(log2^n),二分查找会生成一棵二叉树,查找一个元素时最多只需查找log2^n+1次,即二叉树的层次数。
3.散列查找(哈希查找)
H(k)=k%m;
缺点:容易造成堆积,产生冲突
(1)同义词冲突:两个以上的数据元素要占用同一个地址单元
(2)解决办法:1》开放定址法---线性探查法,
2》拉链法
代码如下(用拉链法解决)
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
typedef struct node
{
int data;
struct node * next;
}ElemSN;
//哈希查找的实现H(k)=k%m,m值自定
void hashsearch(int d[],int n )
{
ElemSN s[13];//先创建一个长度为13的结构体数组
ElemSN *p,*h,*t,*q;
int i,j,k;
h=t=s;
for(i=0;i<13;i++)
{
s[i].data=i;
s[i].next=NULL;//给每个结构体的next指针域赋空
}
for(i=0;i<n;i++)
{
p=(ElemSN *)malloc(sizeof(ElemSN));
p->data=d[i];
p->next=NULL;
k=d[i]%13;
t=&(s[k]);//把s[k]的地址赋给t,即t指向s[k],然后挂链
while(t)
{
q=t;
t=t->next;
}
q->next=p;
}
t=&s[0];//输出取余为0 的结点的值
t=t->next;
while(t)
{
printf("%5d",t->data);
t=t->next;
}
}
int main (void)
{
int d[6]={13,45,465,52,76,87};
hashsearch(d,6);
return 0;
}