Boost::filesystem, std::sort:在排序传递时难以保留信息

Boost::filesystem, std::sort: trouble retaining information on sort passes

本文关键字:保留 信息 排序 filesystem std sort Boost      更新时间:2023-10-16

我试图在包含从boost::filesystem::dictionary_iterator读取的信息的数据类型上使用std::sort。看起来,由于排序算法已经完成了n比较,n是目录中的文件数量,该信息丢失,并且我最终进行了分段故障。Valgrind说我正在使用未初始化的值,并且正在进行无效的读取。

我如何改变我的File数据类型或算法,使信息之间的传递保持?

#include <iostream>
#include <algorithm>
#include <vector>
#include <string>
#include <boost/filesystem.hpp>
namespace fs = boost::filesystem;
struct File {
    fs::path path;
    fs::file_status status;
};
bool comp(const File& a, const File& b) {
    static size_t count = 0;
    std::cout << "Compare function called " << ++count << " times" << std::endl;
    std::string a_filename = a.path.filename().native();
    std::string b_filename = b.path.filename().native();
    return a_filename.compare(b_filename);
}
int main() {
    std::vector<File> vec;
    // Read directory
    fs::directory_iterator it("/etc"), end;
    for (; it != end; it++) {
        File f = *(new File);
        f.path = it->path();
        f.status = it->status();
        vec.push_back(f);
    }
    std::sort(vec.begin(), vec.end(), comp);
    // Clean up
    for (std::vector<File>::iterator it = vec.begin(); it != vec.end(); it++)
        delete &(*it);
    return 0;
}

(这不是我的实际程序,但表现出相同的行为)

在末尾调用compare()是错误的,它返回一个int,可以是-1,0或1,就像strcmp()一样。使用一个简单的std::less()(a_filename, b_filename)调用来代替。还要确保您有单元测试,以确保比较器创建严格弱排序,就像std::sort所要求的那样。

带有内部检查的比较器:

inline bool do_compare(const File& a, const File& b)
{
    /* ... */
} 
bool compare(const File& a, const File& b)
{
    bool const res = do_compare(a, b);
    if(res)
        assert(!do_compare(b, a));
    return res;
}

如果定义了NDEBUG(即禁用assert()),编译器应该能够将其优化为与以前相同的代码量。现在,我希望您在编写按顺序对9.png, 10.png和11.png文件名进行排序的代码时非常愉快。div;)