典型的查找算法分为:
一:顺序查找(线性查找)
二:折半查找(二分查找)
三:分块查找(索引顺序查找)
一:顺序查找(线性查找)
1. 算法基本思想:
让关键字与队列中的数从第一个开始逐个比较,直到找出与给定关键字相同的数为止。
2. 平均查找长度:
(n+1)/2
3. 算法实现:
从顺序表的n个元素中顺序查找关键字为key的元素,若成功返回其下标,否则返回-1
int seqSearch(int array[ ], int n, int key)
{
for(int i=0; i<n; i++)
{
if(array[i] == key)
return i;
return -1;
}
}
二:折半查找(二分查找)
1. 算法基本思想:
设表长为n,low、high和mid分别指向待查元素所在区间的上界、下界和中点,key为给定值
初始时,令low=1,high=n,mid=(low+high)/2
通过key与mid指向的记录比较
若k==r[mid].key,查找成功
若k<r[mid].key,则high=mid-1
若k>r[mid].key,则low=mid+1
重复上述操作,直至low>high时,查找失败
2. 平均查找长度:
log2(n+1)-1
3. 算法实现:
(1) 非递归方式
int binSearch(int array[ ], int n, int key)
{
int low = 0, high = n- 1;
int mid = 0;
while(low <= high)
{
mid= (low+high)/2;
if(key == array[mid])
{
return mid;
}
else if(key > array[mid])
{
low = mid + 1;
}
else
{
high = mid – 1;
}
}
return -1;
}
(2)递归方式
int binsearch(int array[], int low, int high, int key)
{
int mid = 0;
if(low > high)
{
return -1;
}
mid = (low+high)/2;
if(key == array[mid])
{
return mid;
}
else if(key > array[mid])
{
return binsearch(array, mid+1, high, key);
}
else
{
return binsearch(array,low, mid-1, key);
}
}
三:分块查找(索引顺序查找)
1. 算法基本思想:
将查找表分成若干个子表,并对子表建立索引表,查找表的每一个子表由索引表中的索引项确定。
索引项包括两个字段:关键码字段(存放对应子表中的最大关键码值) ;位置字段(存放对应子表的相对查找表的起始位置) ,并且要求索引项按关键码字段有序。
查找过程分为两步:
(1):首先查找索引表,确定待查记录所在块(由于索引项按关键码字段有序,可用顺序查找或折半查找)
(2):再对该分块进行顺序查找。
2. 平均查找长度:
设表共n个结点,分b块,s=n/b
(二分查找索引表)平均查找长度=Log2(n/s+1)+s/2
(顺序查找索引表)平均查找长度=(s*s+2s+n)/(2s)
3. 算法实现:
struct idxTable
{
int key;
int addr;
};
/***************************************************************************
* array: 待查找数组; idx: 索引表
* n: 数组的大小;b: 索引表的大小;key: 待查找的值
* * ***********************************************************************/
int blkSearch(int array[], struct idxTable idx[], int n, int b, int key)
{
int i = 0;
int j = 0;
int low = 0;
int high = 0;
int s = n/b;
if((key < idx[0].key) || (key > idx[b-1].key))
return -1;
for(j = 0; j < b; j++)
{
if(key < idx[j].key)
break;
}
low = idx[j].addr;
high = low + s;
for(j = low; j < high; j++)
{
if(key == array[j])
return j;
}
return -1;
}