我读过一个问题,是否可以在链接列表中应用二进制搜索?
由于链接列表不允许随机访问,因此这看起来几乎不可能。
任何人都有办法吗?
答案 0 :(得分:5)
除了您没有对链表元素进行常量访问之外,主要问题是您没有关于列表长度的信息。在这种情况下,你根本无法将列表“切割”成两半。
如果您对链表长度至少有一个限制,那么问题在O(log n)中是可解决的,确实是跳过列表方法。否则什么都不会让你无法阅读整个列表,因此O(n)。
因此,假设链表已排序,并且您知道其长度(或至少是最大长度),是的,可以在链表上实现某种二进制搜索。但情况并非如此。
答案 1 :(得分:1)
使用纯链表,您不能直接进行二进制搜索,因为链表上的随机访问是O(n)。
如果你需要快速搜索,树状数据结构(R / B树,trie,堆等)提供链表的很多优点(相对便宜的随机插入/删除),同时效率很高在搜索。
答案 2 :(得分:0)
答案 3 :(得分:0)
我曾经为包含排序键的单链表实现了类似的功能。我需要在其中找到几个键(在开始时只知道其中一个键,其余的都依赖于它)并且我想避免一次又一次地遍历列表。我不知道列表长度。
所以,我最终做到了这一点......我创建了256个指针来指向列表元素并使它们指向前256个列表元素。一旦使用了所有256个并且需要257个,我删除了奇数指针值(1,3,5等),将偶数(0,2,4等)压缩到前128个指针中并继续将剩余的一半(128)指针分配给其余的,这次跳过每个其他列表元素。这个过程一直重复到列表的末尾,此时这些指针指向整个列表中等间距的元素。然后,我可以使用256个(或更少)指针进行简单的二进制搜索,将线性列表搜索缩短为原始列表长度的1/256(或1 /无等)。
这不是很花哨或功能强大,但有时可以通过轻微的代码更改来提高性能。
答案 4 :(得分:0)
您可以在链接列表上进行二进制搜索。正如您所说,您没有随机访问权限,但您仍然可以从列表的开头或其他位置查找具有特定索引的元素。因此,可以进行简单的二进制搜索,但与数组的二进制搜索相比较慢。
如果你有一个列表,其中比较比简单的列表遍历要贵得多,那么二进制搜索比线性搜索适当大小的列表便宜。线性搜索需要O(n)
比较和O(n)
节点遍历,而二进制搜索需要O(log n)
比较和O(n log n)
节点遍历。我不确定O(n log n)
绑定是否紧张,其他人是。
答案 5 :(得分:0)
据我所知,无法以二进制搜索方式搜索链接列表。在二进制搜索中,我们通常会发现数组的'mid'值是列表不可能的,因为列表是我们必须严格使用'start'(指向列表的第一个节点的节点)遍历任何我们的列表元素。
在数组中,我们可以使用INDEX转到特定元素,这里没有索引问题(由于链表中的随机访问不可用)。
所以,我认为在通常的做法中,链表不可能进行二进制搜索。
答案 6 :(得分:0)
对于在链表上应用二进制搜索,您可以维护一个变量计数,该计数应该遍历链表并返回节点总数。此外,您还需要在节点类中保留一个int类型的int,例如INDEX,它应该在创建每个新节点时递增。之后,您可以轻松地将链接列表分成两半并对其应用二进制搜索。