使用std :: equal_range查找字符串向量中出现的前缀范围

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了使用std :: equal_range查找字符串向量中出现的前缀范围相关的知识,希望对你有一定的参考价值。

我正在尝试提出一个lambda,它允许std :: equal_range返回一个范围,在该范围内搜索的字符串作为前缀存在。因为这可能没有措辞,一个例子:

给定字符串向量:

  • C: Users 用户安迪文件 screenshot.jpg
  • C:用户鲍勃桌面 file.txt的
  • C:用户鲍勃桌面 picture.png
  • C:用户鲍勃桌面 video.mp4
  • C:用户约翰桌面 note.txt

我希望迭代器返回

  • C: users bob desktop file.txt和
  • C:用户鲍勃桌面 video.mp4。

我如何为完成此操作的std :: equal_range编写比较lambda,或者std :: equal_range不是作业的工具?

答案

我想你只需要让比较器只比较前缀的长度和这样的元素:

std::vector<std::string> v
{
    "C:/users/andy/documents/screenshot.jpg",
    "C:/users/bob/desktop/file.txt",
    "C:/users/bob/desktop/picture.png",
    "C:/users/bob/desktop/video.mp4",
    "C:/users/john/desktop/note.txt",
};

std::sort(std::begin(v), std::end(v));

std::string const prefix = "C:/users/bob/desktop/";

auto lb = std::lower_bound(std::begin(v), std::end(v), prefix);

// For the upper bound we want to view the vector's data as if
// every element was truncated to the size of the prefix.
// Then perform a normal match.
auto ub = std::upper_bound(lb, std::end(v), prefix,
[&](std::string const& s1, std::string const& s2)
{
    // compare UP TO the length of the prefix and no farther
    if(auto cmp = std::strncmp(s1.data(), s2.data(), prefix.size()))
        return cmp < 0;

    // The strings are equal to the length of the prefix so
    // behave as if they are equal. That means s1 < s2 == false
    return false;
});

// make the answer look like we used std::equal_range
// (if that's what's needed)
auto range = std::make_pair(lb, ub);

for(auto itr = range.first; itr != range.second; ++itr)
    std::cout << *itr << '
';

输出:

C:/users/bob/desktop/file.txt
C:/users/bob/desktop/picture.png
C:/users/bob/desktop/video.mp4

解释为什么这个工作想象采取矢量并对其进行排序。然后想象一下访问每个元素并将它们截断为前缀的长度。你将留下一个排序的向量,没有比前缀更长的元素。在那时,一个简单的std::equal_range会做你需要的。因此,我们需要做的就是构造一个比较器,其行为就像容器元素被截断为前缀的长度一样,并在我们的std::equal_range搜索中使用该比较器(或双std::lower_bound/upper_bound搜索)。

以上是关于使用std :: equal_range查找字符串向量中出现的前缀范围的主要内容,如果未能解决你的问题,请参考以下文章

使用 `std::equal_range` 和 `boost::transform_iterator`

std::equal_range 不适用于具有 operator< 定义的结构

查找 vs equal_range 和性能

用于关联容器的 C++ 入门 5ed equal_range

在字符串的 std::map 中查找编译错误,长

使用 C++,尝试使用 for 循环和 std::max 查找向量中的最大单词