Algorithm 对已排序的多个项目进行二进制搜索
假设我有一个长排序列表L={1,2,…,999,1000},和一个短排序列表S={22,255,623,732,876} 在L中,我想搜索S的每个元素。最有效的方法是什么 到目前为止,我提出的方法是:Algorithm 对已排序的多个项目进行二进制搜索,algorithm,binary-search,Algorithm,Binary Search,假设我有一个长排序列表L={1,2,…,999,1000},和一个短排序列表S={22,255,623,732,876} 在L中,我想搜索S的每个元素。最有效的方法是什么 到目前为止,我提出的方法是: 1. Binary search for 22. Record the lower bound=23 2. Binary search for 876. Record the upper bound=875 3. Binary search for 255 in the range [lower
1. Binary search for 22. Record the lower bound=23
2. Binary search for 876. Record the upper bound=875
3. Binary search for 255 in the range [lower bound=23, upper bound=875].
4. Set lower bound=256, and go on..
这是最有效的方法吗?有没有其他方法可以比这种方法收敛得更快
谢谢 一些建议:
1) 首先,尝试查找排序短列表的中间元素(示例中为623),结果是索引
2) 将短列表分为下半部分(所有元素小于中间元素)和上半部分(所有元素大于中间元素)
3) 对于下半部分,我们开始从长列表的0
到index
,对于上半部分,我们开始从index+1
到n
(n是长列表的长度)
4) 对两半部分递归地执行步骤1。您的想法是跟踪边界并缩小搜索范围。从左端和右端交替查找条目的方法与从左到右遍历小数组并调整下限一样好。(除非你知道S中钥匙的分配情况。)
我认为您应该递归地处理小数组,并在每个递归、二进制搜索样式上对半进行处理。在数组L
中查找623
,并找到索引k
。接下来递归到左边的子数组,并在L[0…k]
中的{2255}
中查找条目。然后在右侧递归并在L[k+1…| L |]
中查找条目{723,876}
,因为您在其中一条评论中提到您的列表很大,如果较短的列表的长度与较长列表的长度相当,您可以在两个列表的开头设置两个指针,在每一步中,移动一个指向右边较小元素的元素。只要两个指针指向相同的值,就可以找到匹配项。这将是O(s+l)
,如果s
接近l
(s
是较短列表的长度,l
是较长列表的长度),这将比naiveO(s log l)
快。对较短列表进行排序,并对较长列表中的每个项目对较短列表进行二进制搜索。这是最快的速度。@BartoszMarcinkowski,在较长列表的长度上是线性的,它肯定没有得到的快:)无论如何,你必须阅读较长的列表才能决定它是否包含元素,除非它被排序。我们不知道它是否被排序。根据OP建议的算法,我觉得长列表已经排序了。好吧,我不假设没有明确说明的内容:)你是指2吗。划分长列表?@blastfurny我想你误读了我的答案:),我建议OP从短列表的中间开始搜索,这缩小了搜索短列表中其他元素的范围,这不是典型的二进制搜索:)(实际上是嵌套二进制搜索)@Ishamael实际上两者都有,短列表的下半部分元素需要在长列表的下半部分进行搜索(从0到索引
,其中索引
是对中间元素进行二进制搜索的结果)@PhamTrung谢谢!听起来有很多编程,但值得一提,因为我的列表很大。@Phamtrong我不擅长复杂性理论,但你认为你的alg大约是O(logS*logL)吗?很感兴趣:)谢谢:)不幸的是,我的短名单大约有2万人,长名单大约有1000万人。。