【问题标题】:what's wrong with my recursive binary search algorithm?我的递归二进制搜索算法有什么问题?
【发布时间】:2021-11-17 21:16:10
【问题描述】:

我尝试在像一维数组这样的结构中搜索数据,但它总是告诉我目标数据尚未找到,尽管我已经完全按照它的算法。现在我完全糊涂了

下面是我如何定义函数

int RecBinarySearch (int a[], int low, int high, int key) {

    int mid{ };

    if (high >= low  ) {
        mid =  low + (high-low)/2;

        if (key == a[mid]) return mid;
        if (key > a[mid]) RecBinarySearch(a, mid + 1, high, key);
        if (key < a[mid]) RecBinarySearch(a, low, mid - 1, key);
    }

    return -1;
}

在这里你可以看到我是如何定义我的数组的

int n{};
int* a = new int [n] {};

【问题讨论】:

  • 注意:去掉c标签,你的代码是C++,不是C。不同的语言,不同的解决方案。
  • @LucaPolito int a[n]; C :)。 RecBinarySearch 与 C 兼容(除了这个 mid{}),c 标记应该保留
  • @tstanisl 我明白你的意思。但总的来说,C 解决方案可能并不理想(没有利用 C++ 的所有特性),C++ 解决方案在 C 中可能是错误的。
  • @tstanisl int* a = new int [n] {}; 不是 C。int mid{ }; 不是 C。但它的编写方式就像您编写 C 代码一样。
  • 你应该edit你的问题并显示minimal reproducible example

标签: c++ recursion search binary-search


【解决方案1】:

这就是你想要的:

#include <iostream>

int RecBinarySearch(int a[], int low, int high, int key)
{
  if (high >= low)
  {
    int mid = low + (high - low) / 2;

    if (key == a[mid])
      return mid;
    if (key > a[mid])
      return RecBinarySearch(a, mid + 1, high, key);  // you forgot the return statement
    if (key < a[mid])
      return RecBinarySearch(a, low, mid - 1, key);   // you forgot the return statement
  }

  return -1;
}

int main()
{
  int values[] = { 1,3,4,5,6,7 };   // must be sorted

  // check if we find each of the values contained in values
  for (auto v : values)
  {
    if (RecBinarySearch(values, 0, 7, v) == -1)
    {
      std::cout << v << " not found\n";
    }
  }

  int valuesnotcontained[] = {0,2,8,10};

  // check we don't find values not contained in values
  for (auto v : valuesnotcontained)
  {
    if (RecBinarySearch(values, 0, 7, v) != -1)
    {
      std::cout << v << " should not be found\n";
    }
  }
}

它包括一些基本的测试代码。

【讨论】:

  • 我已经写过了,但我需要的是递归
  • @SanaAllahKheiri 但在我的答案中的代码中有 is 递归......不同之处在于,在我的代码中我使用了 return 语句,但你没有。
【解决方案2】:

当您递归调用一个应该返回某些内容的函数时,您需要返回递归调用将返回的内容。

    if (key > a[mid]) return RecBinarySearch(a, mid + 1, high, key);
    if (key < a[mid]) return RecBinarySearch(a, low, mid - 1, key);

好吧,不要从字面上理解。对于大多数分而治之的递归算法和贪婪算法来说都是如此,其中递归调用旨在找到答案。然后,这个答案必须向上传播。在其他情况下,递归调用只是找到解决方案的一部分。在这些情况下,需要将结果合并到最终答案中。

但是,关键是您忽略了递归调用的返回结果,这会触发一个错误,您将返回 -1 而不是调用找到的答案。


请注意,C++ 包括 binary_search(而 C 包括 bsearch)。

【讨论】:

  • 非常感谢兄弟,非常有用,这是我非常想念 10 Q 的真正意义
  • @SanaAllahKheiri 考虑使用tour
【解决方案3】:
    return (key == a[mid])
           ? mid:
           (key > a[mid])
           ? RecBinarySearch(a, mid, high, key):
           (key < a[mid]) 
           ?RecBinarySearch(a, low, mid, key):
           -1;

当然,假设a[] 已正确排序。

【讨论】:

  • 虽然每个条件立即返回意味着它不会改变代码的结果,但在第二个和第三个条件下使用else if 感觉更正确(第三个可能只是else).
  • 嵌套?: 是混淆代码的完美方式。不要这样做。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-09-06
  • 2021-12-15
相关资源
最近更新 更多