Data Structures Algorithms 简明教程
Exponential Search Algorithm
指数级搜索算法针对输入数组的一个范围,它假定所需元素必须存在于该范围中,并在该特定小范围内执行二分搜索。此算法也称为加倍搜索或手指搜索。
它类似于跳跃搜索,将已排序的输入分成多个块,并进行小规模搜索。然而,在对块进行划分来执行计算和应用的小规模搜索类型(跳跃搜索应用线性搜索和指数搜索应用二分搜索)时会出现差异。
因此,这种算法以指数方式跳过 2 的各个幂。用更简单的语言来说,对使用 pow(2, k) 划分的块执行搜索,其中 k 是大于或等于 0 的整数。一旦位于 pow(2, n) 位置的元素大于关键字元素,便对当前块执行二分搜索。
Exponential Search Algorithm
在指数搜索算法中,跳跃从数组的第 1 个索引开始。因此,我们在算法的第一步手动比较第一个元素。
步骤 1 − 将数组中的第一个元素与关键字进行比较,如果找到匹配项,则返回第 0 个索引。
步骤 2 − 初始化 i = 1,并将数组的第 i 个元素与要搜索的关键字进行比较。如果匹配,则返回该索引。
步骤 3 − 如果元素不匹配,则在 2 的各个幂中按指数跳过该数组。因此,现在算法比较位于增量位置的元素。
步骤 4 − 如果找到匹配项,则返回该索引。否则,重复步骤 2,直到位于增量位置的元素大于要搜索的关键字为止。
步骤 5 − 由于下一个增量比关键字的元素高并且输入已排序,因此算法对当前块应用二分搜索算法。
步骤 6 − 如果找到匹配项,则返回关键字所在的索引;否则,确定为未成功搜索。
Pseudocode
Begin
m := pow(2, k) // m is the block size
start := 1
low := 0
high := size – 1 // size is the size of input
if array[0] == key
return 0
while array[m] <= key AND m < size do
start := start + 1
m := pow(2, start)
while low <= high do:
mid = low + (high - low) / 2
if array[mid] == x
return mid
if array[mid] < x
low = mid + 1
else
high = mid - 1
done
return invalid location
End
Analysis
即使它被称为指数搜索,它也不会以指数时间复杂度执行搜索。但是,正如我们所知,在此搜索算法中,执行的基本搜索是二分搜索。因此,指数搜索算法的时间复杂度与二分搜索算法的时间复杂度相同, O(log n) 。
Example
为了更好地、更简单地理解指数搜索算法,让我们使用指数搜索算法在示例输入数组中搜索元素−
提供给搜索算法的排序输入数组如下−
让我们在给定的数组中搜索元素 81 的位置。
Step 1
将数组的第一个元素与关键字元素 81 进行比较。
数组的第一个元素是 6,但要搜索的关键字元素是 81;因此,由于没有找到匹配项,此跳跃从第 1 个索引开始。
Step 2
在初始化 i = 1 之后,将关键字元素与第一个索引中的元素进行比较。此处,第 1 个索引中的元素与关键字元素不匹配。因此,它再次以指数方式按 2 的幂进行递增。
索引增加到 2m = 21 = 将第 2 个索引中的元素与关键字元素进行比较。
仍然不匹配,因此再次进行递增。
Step 3
索引再次以指数方式按 2 的幂递增。
22 = 4 = 将第 4 个索引中的元素与关键元素进行比较,但尚未找到匹配项。
Step 4
索引再次成倍增加。这一次,将第 8 个索引中的元素与关键元素进行比较,但尚未找到匹配项。
但是,第 8 个索引中的元素大于关键元素。因此,将二分搜索算法应用于当前元素块。
Step 5
当前元素块包括索引 [4, 5, 6, 7] 中的元素。
在这个元素块上应用小规模二分搜索,其中计算中值为第 5 个元素。
Step 6
在中值元素处未找到匹配项,并得出期望的元素大于中值元素的结论。因此,搜索发生在块的右半部分。
现在,中值设置为第 6 个元素 -
Step 7
元素仍未在第 6 个元素中找到,因此现在在中值元素的右半部分进行搜索。
下一个中值设置为第 7 个元素。
在这里,在第 7 个索引处找到了元素。