如何解析 CRT 函数形成的日期字符串?
How to parse date string which is formed by the CRT function?
我现在正在开发一个 Windows 驱动的 C++ 项目。并且有一个函数可以组成一个文件名,其中包含日期部分。它使用 wcsftime C 运行时库函数通过 "%x"
格式化代码来格式化日期部分。此代码对应于
%x Date representation for the locale
如文档所述。
现在,我需要检查哪些文件与某个日期范围匹配。所以,我需要将文件名的这个日期部分解析回日期并执行比较。但是,我遇到了麻烦:该怎么做?我没有找到任何可以完成这项工作的 CRT 函数。此外,为了解析该字符串,获取当前语言环境的格式字符串(如“dd-mm-yyyy”)可能会好得多。但是我没有找到任何方法。
注意了,是关于CRT功能的。例如,它的语言环境与 GetLocaleInfo 使用的语言环境不同。
最大的问题是,如果您知道创建字符串中日期的语言环境。
如果您在同一台机器上,那么您可以使用 time_get 中描述的函数 here。
这样就可以得到日期中日、月、年的顺序。有了它,您就可以先构建一个 std::regex
来提取数字,然后将这些数字分配到相应的日期段中。
正则表达式可能看起来像 R"(\d{1,4}[.\/,;]\d{1,4}[.\/,;]\d{1,4})"这将匹配由一些典型的日期分隔符分隔的 3 位数字组。
然后,通过日期顺序的知识,您可以从字符串中提取日、月和年。
一些示例代码:
#include <iostream>
#include <locale>
#include <string>
#include <regex>
#include <iomanip>
// Example for year/month/day formated string
std::string fileName{"file7_234x2021/5/23abc.txt"};
std::regex re{R"((\d+)[\.\\/\,\;](\d{1,4})[\.\\/\,\;](\d{1,4}))"};
int main() {
std::smatch sm{};
if (std::regex_search(fileName,sm,re)) {
int year = std::stoi(sm[1]);
int month = std::stoi(sm[2]);
int day = std::stoi(sm[3]);
std::cout << std::right << std::setfill('0') << std::setw(2) << day << '-' << std::setw(2) << month
<< '-'<< std::setw(4) << year << '\n';
}
}
如果你不知道日期顺序,那么你可能会遇到很大的问题,只能通过一些启发式的方法来找出什么是什么。
例如
- 31 以上的数字是年
- 12 以上的数字是天(或年)
但是,不知何故容易出错。 . .
一个简单的解决方案是 forward:使用相同的模式生成文件名,但测试日期为 2001-02-03
。结果会告诉你年月日的顺序。
我现在正在开发一个 Windows 驱动的 C++ 项目。并且有一个函数可以组成一个文件名,其中包含日期部分。它使用 wcsftime C 运行时库函数通过 "%x"
格式化代码来格式化日期部分。此代码对应于
%x Date representation for the locale
如文档所述。
现在,我需要检查哪些文件与某个日期范围匹配。所以,我需要将文件名的这个日期部分解析回日期并执行比较。但是,我遇到了麻烦:该怎么做?我没有找到任何可以完成这项工作的 CRT 函数。此外,为了解析该字符串,获取当前语言环境的格式字符串(如“dd-mm-yyyy”)可能会好得多。但是我没有找到任何方法。
注意了,是关于CRT功能的。例如,它的语言环境与 GetLocaleInfo 使用的语言环境不同。
最大的问题是,如果您知道创建字符串中日期的语言环境。
如果您在同一台机器上,那么您可以使用 time_get 中描述的函数 here。
这样就可以得到日期中日、月、年的顺序。有了它,您就可以先构建一个 std::regex
来提取数字,然后将这些数字分配到相应的日期段中。
正则表达式可能看起来像 R"(\d{1,4}[.\/,;]\d{1,4}[.\/,;]\d{1,4})"这将匹配由一些典型的日期分隔符分隔的 3 位数字组。
然后,通过日期顺序的知识,您可以从字符串中提取日、月和年。
一些示例代码:
#include <iostream>
#include <locale>
#include <string>
#include <regex>
#include <iomanip>
// Example for year/month/day formated string
std::string fileName{"file7_234x2021/5/23abc.txt"};
std::regex re{R"((\d+)[\.\\/\,\;](\d{1,4})[\.\\/\,\;](\d{1,4}))"};
int main() {
std::smatch sm{};
if (std::regex_search(fileName,sm,re)) {
int year = std::stoi(sm[1]);
int month = std::stoi(sm[2]);
int day = std::stoi(sm[3]);
std::cout << std::right << std::setfill('0') << std::setw(2) << day << '-' << std::setw(2) << month
<< '-'<< std::setw(4) << year << '\n';
}
}
如果你不知道日期顺序,那么你可能会遇到很大的问题,只能通过一些启发式的方法来找出什么是什么。
例如
- 31 以上的数字是年
- 12 以上的数字是天(或年)
但是,不知何故容易出错。 . .
一个简单的解决方案是 forward:使用相同的模式生成文件名,但测试日期为 2001-02-03
。结果会告诉你年月日的顺序。