排序的双向链表中的二进制搜索与线性搜索

时间:2019-03-24 10:41:39

标签: c

我正在使用双链表进行有关图书馆管理的大学项目。双向链表在排序时保存书籍的ID。

我试图计算线性搜索和二进制搜索的最坏情况所花费的时间。结果如下:

Binary search: 0.311ms
Linear search: 0.228ms
[Number of inputs(id's): 10000000]

我的问题:

即使二进制搜索需要进行O(logn)比较,但是由于事实的原因,经过的时间更多,但遍历了O(n)才找到中间值。有没有更好的搜索算法来处理排序的双链表,而不是麻烦的线性搜索?

我的查找二进制搜索所需中间值的实现:

struct node* middle(node* start, node* last) 
{ 
    if (start == NULL) 
        return NULL; 
    struct node* slow = start; 
    struct node* fast = start -> next; 
    while (fast != last) 
    { 
        fast = fast -> next; 
        if (fast != last) 
        { 
            slow = slow -> next; 
            fast = fast -> next; 
        } 
    } 
    return slow; 
} 

3 个答案:

答案 0 :(得分:0)

您的比较必须非常慢才能证明所有导航的合理性。就目前而言,我想不出一种比线性搜索更好的方法。如果您可以更改结构和CRUD,则可以肯定地索引关键点(“ A”从这里开始,“ B”从这里开始,等等),这将使您能够更好地猜测线性搜索的开始和方向。

我认为您会发现,链表(无论是双链还是双链)对于随机查找或按顺序更新都不是一个好选择。使用B树似乎更适合您在问题和评论中概述的情况。

答案 1 :(得分:0)

  

经过的时间更多是由于这样的事实,即经过O(n)遍历直到找到中间值。

在链接列表中插入新元素时,您也可以像跟踪第一个和最后一个一样跟踪中间元素。尽管insert函数会更复杂。
我将使用具有4个字段的链表的结构:

  • 起始节点
  • 中间节点
  • 最后一个节点
  • 长度

答案 2 :(得分:0)

二元搜索的比较次数达到了 O(log N)复杂度。与数组一起使用时,访问数组的第i个元素的时间是固定的,因此不会影响整体时间复杂度。

使用列表(单链接或双链接)访问第i个元素需要执行 i 步骤。在您的示例中,访问中间元素的步骤与列表的长度成比例。结果,此搜索的复杂度仍然是 O(log N)比较,但是 O(n)用于选择要比较的项目,这成为主要因素