是否可以根据复杂的标准使用 std::sort() 对字符串向量进行排序?

Is it possible to sort a vector of string with std::sort(), based on a complex criteria?

提问人:Jean-Milost Reymond 提问时间:2/17/2022 更新时间:3/15/2022 访问量:51

问:

我需要对包含文件夹名称的文件夹进行排序,使父文件夹始终位于其所有子文件夹之后,例如:std::vector<std::wstring>

C:\Main\App\QtGraphicalEffects\private
C:\Main\App\QtGraphicalEffects
C:\Main\App\Qt\labs\platform
C:\Main\App\Qt\labs
C:\Main\App\Qt
C:\Main\App
C:\Main\

为了达到这样的排序,我可以使用气泡排序算法,如下所示:

void BubbleSortDirs(std::vector<std::wstring>& dirs)
{
    bool swapped = false;

    do
    {
        swapped = false;

        for (std::size_t i = 0; i < dirs.size() - 1; ++i)
            // swap positions if first dir is entirely contained in the second
            if (dirs[i] != dirs[i + 1] && dirs[i + 1].find(dirs[i]) == 0)
            {
                std::swap(dirs[i], dirs[i + 1]);
                swapped = true;
            }
    }
    while (swapped);
}

这段代码运行良好,但我觉得应该有更好的解决方案。因此,我尝试使用该功能来优化我的排序,至少提供更优雅的解决方案。std::sort

我尝试了以下实现:

bool SortDirs(const std::wstring& first, const std::wstring& second)
{
    // swap positions if first dir is entirely contained in the second
    return (first == second || first.find(second) == 0);
}

...

std::sort(dirs.begin(), dirs.end(), SortDirs);

我期望这将提供与函数相同的结果,但事实并非如此,结果在几个位置都失败了。在这一点上,我强烈怀疑它不适合像我试图应用的复杂排序标准。std::sort()BubbleSortDirs()std::sort()

所以我的问题是:

  • 我的调用没有提供预期结果的原因是什么?std::sort
  • 有没有办法使用该函数实现上述排序?std::sort()
  • 如果是,我做错了什么?
  • 如果不是,上述函数是实现这种排序的最佳方式,还是存在更好的东西?BubbleSortDirs()
字符串 排序 std bubble-sort

评论

1赞 pm100 2/17/2022
你有没有调试为什么它失败了,我的意思是它不难做到
1赞 pm100 2/17/2022
如果目录的末尾总是有 \,则逻辑有效,就像示例中的最后一个一样
0赞 Jean-Milost Reymond 2/17/2022
@pm100感谢您的回答。我不同意最后的 \,事实上,我认为没有理由在子项中找不到父文件夹,无论有没有最后的 \。对于调试,是的,我做到了,但是就像 std::sort 只遍历向量一次,要么我什么都不懂,要么 std::sort 不适合我的排序标准。这就是我上面问题的目的:确定我是否误解了 std::sort 的工作原理。
1赞 pm100 2/17/2022
好吧,您的代码使用尾随 \ 正确排序结果,如果没有它就无法正确排序(正如您指出的那样)。我的意思是我实际上运行了你的代码,用这 7 个输入字符串,做了一个随机洗牌,然后排序,结果是错误的。然后我调试了函数,将 \ 添加到所有字符串的末尾并重新运行测试。然后,字符串将按您想要的顺序显示出来。如果您愿意,可以忽略此信息
0赞 Jean-Milost Reymond 2/17/2022
@pm100再次感谢您的回答。我不知道为什么在您的系统上有或没有最后的 \ 时排序会有所不同,但我在我的代码中测试了您的建议,不幸的是,问题保持不变。最后,我可以用一种非常简单的方式解决它:std::sort(dirs.rbegin(), dirs.rend());

答:

0赞 Jean-Milost Reymond 3/15/2022 #1

我终于以这种方式解决了我的问题:

std::sort(dirs.rbegin(), dirs.rend());