首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >如何比较time_t和std::filesystem::file_time_type

如何比较time_t和std::filesystem::file_time_type
EN

Stack Overflow用户
提问于 2018-07-10 20:07:40
回答 4查看 7.5K关注 0票数 12

我正在将一些代码从boost::filesystem转换为std::filesystem。以前的代码使用boost::filesystem::last_write_time(),它返回一个time_t,所以直接比较我已经持有的time_t对象非常简单。顺便说一句,我持有的这个time_t从很久以前保存的文件内容中读取的,所以我不得不使用这个“自unix时代以来的时间”类型。

std::filesystem::last_write_time返回一个std::filesystem::file_time_type。是否有一种可移植的方法将file_time_type转换为time_t,或者以其他方式对这两个对象进行可移植性比较?

代码语言:javascript
运行
复制
#include <ctime>
#include <filesystem>

std::time_t GetATimeInSecondsSince1970Epoch()
{
    return 1207609200;  // Some time in April 2008 (just an example!)
}

int main()
{
    const std::time_t time = GetATimeInSecondsSince1970Epoch();
    const auto lastWriteTime = std::filesystem::last_write_time("c:\\file.txt");

    // How to portably compare time and lastWriteTime?
}

编辑:请注意,last_write_time声明它假设时钟是实现to_time_t函数的std::chrono::system_clock。这个假设并不总是正确的,也不在我的平台(VS2017)上。

EN

Stack Overflow用户

发布于 2022-06-02 14:18:53

这是我在Windows、MacOS和Linux上使用的填充程序。不幸的是,Clang和GCC还没有file_clock支持,而且对Windows的支持也绑定到最近的10+版本中。请参阅:https://github.com/microsoft/STL/issues/1911

代码语言:javascript
运行
复制
// Copied from Boost: filesystem/src/operations.cpp
// these constants come from inspecting some Microsoft sample code
#ifdef _WIN32
inline std::time_t to_time_t(FILETIME const& ft) BOOST_NOEXCEPT {
    uint64_t t = (static_cast<uint64_t>(ft.dwHighDateTime) << 32) | ft.dwLowDateTime;
    t -= 116444736000000000ull;
    t /= 10000000u;
    return static_cast<std::time_t>(t);
}
#else
// Copied from Stackoverflow
template<typename TP>
std::time_t to_time_t(TP tp) {
    using namespace std::chrono;
    auto sctp = time_point_cast<system_clock::duration>(tp - TP::clock::now() + system_clock::now());
    return system_clock::to_time_t(sctp);
}
#endif

// Use this polyfill until everyone supports C++20
// This code is highly depended on the implementation
time_t PortableLastWriteTime(const std::string& File) {
#ifdef _WIN32
    // We cannot use the C++20 and filesystem due to this incompatibility/error: https://github.com/microsoft/STL/issues/1911
    // This problem makes this request to fail on Windows older than Windows 10 (1903) and somehow Server 2019 completely
    HANDLE handle = CreateFile(File.c_str(), GENERIC_READ, FILE_SHARE_DELETE | FILE_SHARE_READ | FILE_SHARE_WRITE, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL | FILE_FLAG_BACKUP_SEMANTICS, NULL);
    FILETIME lwt;
    if (!::GetFileTime(handle, NULL, NULL, &lwt)) {
        CloseHandle(handle);
        return 0;
    }
    CloseHandle(handle);
    return to_time_t(lwt);
#elif __GLIBCXX__
    auto ftime = std::filesystem::last_write_time(File);
    return to_time_t(ftime);
#elif _LIBCPP_VERSION
    auto ftime = std::filesystem::last_write_time(File);
    return decltype(ftime)::clock::to_time_t(ftime);
#elif __CORRECT_CPP20_VERSION
    // This is the correct C++20 usage when compilers have full compatibility
    const auto fileTime = std::filesystem::last_write_time(File);
    const auto systemTime = std::chrono::clock_cast<std::chrono::system_clock>(fileTime);
    const auto time = std::chrono::system_clock::to_time_t(systemTime);
    return time;
#else
    Unsupported compiler !
#endif
}
票数 0
EN
查看全部 4 条回答
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/51273205

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档