通过对已排序的向量

时间:2017-04-07 15:32:27

标签: c++ algorithm vector binary-search

我一直在尝试使用二进制搜索来获取向量中元素的位置,没有循环,没有任何东西,只是来自库algorithm的二进制搜索函数。

由于二进制搜索功能仅适用于已排序的容器类型,因此我不知道如何获取原始向量的搜索元素的位置,因为在对矢量进行排序后,搜索元素的位置可能与在原始载体。

我使代码与std::find一起使用,但我的主要目标是仅使用二进制搜索功能。

代码:

#include <iostream>
#include <vector>
#include <algorithm>

int main()
{
    std::vector<int> v {1, 10, 100, -11, -112, -17, 44, -99, 99, 558};

    std::vector<int> sorted = v;
    std::sort(sorted.begin(), sorted.end());

    std::cout << "Enter a number: ";
    int number;
    std::cin >> number;

    if(std::binary_search(sorted.begin(), sorted.end(), number) == false)
    {
        std::cout << "There is no entered number.";
    }
    else
    {
        std::cout << "Number is located on position: ";
        std::cout << std::find(v.begin(), v.end(), number) - v.begin();
    }
    return 0;
}

输出示例:

Enter a number: 99
Number is located on position: 8

Enter a number: -546
There is no entered number.

因此,如果有人能帮助我使用二进制函数而不是使用std::find或者给我一些想法,我将非常感激。

谢谢:)

2 个答案:

答案 0 :(得分:3)

如果你想进行二进制搜索并将结果引用回原始的未排序数组 - 你需要进行索引排序和搜索 - 而不是对副本进行排序和搜索在数组中,您对原始数组中的索引数组进行操作。类似的东西:

std::vector<int> v {1, 10, 100, -11, -112, -17, 44, -99, 99, 558};

std::vector<int> sort_indexes(v.size());
for (size_t i = 0; i < v.size(); ++i)
    sort_indexes[i] = i;

std::sort(sort_indexes.begin(), sort_indexes.end(),
          [&v](int a, int b)->bool { return v[a] < v[b]; });

std::cout << "Enter a number: ";
int number;
std::cin >> number;

auto found = std::lower_bound(sort_indexes.begin(), sort_indexes.end(), number,
                              [&v](int a, int b)->bool { return v[a] < b; } );

if (found == sort_indexes.end() || v[*found] > number) {
    std::cout << "There is no entered number." << std::endl;
} else {
    std::cout << "Number is located on position: " << *found << std::endl;
}

答案 1 :(得分:1)

NathanOliver指出,无法对未排序的数据进行二元搜索。

如果您的向量保证最多只有一次,并且您不希望更改顺序,则可以保留一个地图,以保持您的向量的每个int的索引包含。

map<int, size_t> idxMap;

您还可以使用std::find_if进行线性搜索

int valueToFind;
vector<int>::const_iterator it = std::find_if(v.begin(), v.end(), [valueToFind](int entry) { return entry == valueToFind;)};

如果您不受内存限制并希望进行大量搜索,我建议您使用第一个选项。