c++oding="utf-8" ?>
getfiletime函数用于获取windows文件的创建、最后访问和最后修改时间,返回三个filetime结构(自1601年1月1日utc起的100纳秒计数),需先用createfile获取有效句柄,并配合filetimetosystemtime等函数转换为可读时间。

Windows 下用 GetFileTime 获取创建/修改时间
Windows API 提供了直接、可靠的方式:调用 GetFileTime,它返回三个 FILETIME 结构(创建、最后访问、最后修改)。注意:FILETIME 是 64 位整数,表示自 1601-01-01 UTC 起的 100 纳秒数,不能直接当时间戳用。
实操要点:
- 必须先用
CreateFile打开文件(哪怕只读),获得HANDLE;不能对路径字符串直接调用 - 记得检查返回值——
GetFileTime失败时返回FALSE,常见原因是权限不足或句柄无效 - 用
FileTimeToLocalFileTime+FileTimeToSystemTime转成可读的SYSTEMTIME,否则你看到的只是大数字 - “最后访问时间”在 NTFS 上默认被禁用(为提升性能),所以别依赖它;“创建时间”和“修改时间”始终可用
HANDLE h = CreateFile(L"test.txt", GENERIC_READ, FILE_SHARE_READ, nullptr, OPEN_EXISTING, 0, nullptr);
FILETIME ftCreate, ftModify;
if (GetFileTime(h, &ftCreate, nullptr, &ftModify)) {
SYSTEMTIME st;
FileTimeToSystemTime(&ftModify, &st); // 转成年月日时分秒
printf("%d-%02d-%02d %02d:%02d:%02d\n", st.wYear, st.wMonth, st.wDay, st.wHour, st.wMinute, st.wSecond);
}
CloseHandle(h);
Linux/macOS 下用 stat 获取 st_ctime 和 st_mtime
POSIX 系统没有“创建时间”概念,stat 结构里的 st_ctime 是“状态更改时间”(如权限、所有者变更),不是 Windows 意义上的创建时间。真正能用的只有 st_mtime(内容最后修改)和 st_atime(最后访问)。
关键细节:
-
st_ctime容易被误认为创建时间,但它在文件重命名、chown、chmod后都会更新,不可靠 - 获取纳秒精度需用
statx(Linux 4.11+),但移植性差;普通stat只保证秒级,部分系统支持st_mtim.tv_nsec(需定义_GNU_SOURCE) - 路径传给
stat前要确保是绝对路径或当前工作目录下存在,符号链接默认被解引用;要用lstat获取链接本身的元数据
struct stat sb;
if (stat("test.txt", &sb) == 0) {
printf("Modify: %s", ctime(&sb.st_mtime)); // 秒级,带换行
printf("Change: %s", ctime(&sb.st_ctime));
}
C++17 std::filesystem::last_write_time 能否跨平台?
可以读取修改时间,但创建时间完全不支持:std::filesystem 标准里根本没有创建时间接口。C++20 也没加。这意味着即使你用 last_write_time 写出看似跨平台的代码,Windows 的创建时间依然无法通过标准库拿到。
现实约束:
-
last_write_time返回file_time_type,是实现定义的时钟类型(通常是system_clock或自定义纪元),转本地时间需小心时区处理 - 某些旧版 libstdc++(GCC 8 之前)或 MSVC 早期版本对
last_write_time支持不全,可能抛filesystem_error - 想同时拿创建+修改时间?只能 Windows 用 WinAPI,Linux/macOS 接受没有创建时间的事实,或改用第三方库(如 Boost.Filesystem 的
creation_time在 Windows 有实现,Linux 仍 fallback 到st_ctime)
为什么跨平台统一获取创建时间几乎不可能?
根本原因在于文件系统语义差异:NTFS 存储明确的创建时间戳;ext4、APFS 等根本不记录该字段。Linux 内核曾讨论过增加 btime(birth time),但至今未稳定进入主线,glibc 也未暴露对应接口。用户态工具(如 stat -c '%w' file)在多数发行版上显示 “-” 就是明证。
工程建议:
- 如果业务逻辑强依赖创建时间(比如审计、去重),Windows 可用
GetFileTime,Linux 必须自己记录(例如首次写入时存入扩展属性或数据库) - 不要试图用
st_ctime模拟创建时间——它在mv、touch -a、甚至某些备份工具运行后就会变 - 同一份代码里混用 WinAPI 和 POSIX 调用时,务必用
#ifdef _WIN32隔离,且测试双平台的错误路径(比如文件不存在、权限拒绝)
最常被忽略的一点:很多开发者以为“跨平台 = 写一次跑两边”,但文件时间这种底层元数据,本质是操作系统与文件系统的契约,标准库只能做最小公约数。硬要统一,代价是放弃准确性或引入不可控依赖。
C++免费学习笔记(深入):立即使用
在学习笔记中,你将探索 C++ 的入门与实战技巧!











