C++ 获取iso 8601时间戳c+之前和之后的设置时间+;
给定一个标准ISO 8601时间戳,是否有一种简单的方法可以从原始时间戳之前的20分钟和之后的20分钟获得时间戳 举个例子C++ 获取iso 8601时间戳c+之前和之后的设置时间+;,c++,c++11,C++,C++11,给定一个标准ISO 8601时间戳,是否有一种简单的方法可以从原始时间戳之前的20分钟和之后的20分钟获得时间戳 举个例子 2010-01-25 18:02:00 我希望返回一两个函数, 2010-01-25 17:48:00和2010-01-25 18:22:00 我放弃的解决方案相当麻烦,我使用s.substr(14,2)来获取分钟数,s.substr(12,2)来获取小时数,将小时和分钟字符串转换为int,如果分钟数大于60或小于0,则使用条件减去或添加分钟值。有更好/更简单的方法吗?
2010-01-25 18:02:00
我希望返回一两个函数,
2010-01-25 17:48:00
和2010-01-25 18:22:00
我放弃的解决方案相当麻烦,我使用s.substr(14,2)
来获取分钟数,s.substr(12,2)
来获取小时数,将小时和分钟字符串转换为int,如果分钟数大于60或小于0,则使用条件减去或添加分钟值。有更好/更简单的方法吗?您可以:
struct tm
struct tm
struct tm
< >从C或C++标准查找<代码> MKTime[()] < /代码>。要将ISO 8601时间转换为
struct tm
(或者可以使用sscanf()
,或者…),您需要类似于strtime()的东西。然后复制两个结构副本,将tm_min
一个调整+20,另一个调整-20,调用mktime()
,然后调用strftime()
这将适用于C和C++98、C++2003以及C++2011。如果您只想让它与C++2011一起工作,那么您需要转到std::chrono
示例代码
此代码是针对C++的,因为它是头文件,但是可以通过改变为<代码> <代码>和<代码> <代码>转换成C。是的,它可能不算是“好”C++;它当然会让您做出一些接口决策。但它确实完成了任务。(对于纯C++,可以删除引用<代码>结构> <代码>)< /P>
2012-12-31 23:59:00后20分钟是几点?我想没有简单的方法。@BoPersson是的,是的,我甚至没有想到+1这种情况,那些C++11次I/O操纵器确实很方便!一个可能的改进:您可以通过将delta
的类型更改为std::chrono::minutes
来增加的类型安全性。它确实使用户代码更加冗长,但也使20
的实际含义不含糊。另一方面,函数名也努力消除20
的歧义。所以这不是什么大问题,只是另一个设计决策。@HowardHinnant:如果我们想接受std::duration
,最好将tm
转换为时间点。更新了答案来说明这一点。是的,我就是这么想的。但是您最初使用mktime
来规范化tm
也很优雅。我敢肯定这两个人做家庭作业都太过分了。:-)如果你真的想把这匹马打死,你可以在Rep
和Period
上设置模板,使参数std::chrono::duration
。这使得增加iso\u时间
在持续时间
参数中不会“过于通用”。
#include <ctime>
#include <string>
#include <sstream>
#include <iostream>
#include <iomanip>
std::string increase_minutes(const std::string& input, int delta) {
struct tm tm;
constexpr auto format = "%Y-%m-%d %T";
std::istringstream iss (input);
iss >> std::get_time(&tm, format);
tm.tm_min += delta;
mktime(&tm);
std::ostringstream oss;
oss << std::put_time(&tm, format);
return oss.str();
}
int main() {
auto s = "2012-12-31 23:59:00";
std::cout << increase_minutes(s, 20) << std::endl;
std::cout << increase_minutes(s, -20) << std::endl;
}
#include <ctime>
#include <string>
#include <sstream>
#include <iostream>
#include <iomanip>
#include <chrono>
template <typename R, typename P>
std::string increase_iso_time(const std::string& input,
const std::chrono::duration<R, P>& duration) {
struct tm tm;
constexpr auto format = "%Y-%m-%d %T";
std::istringstream iss (input);
iss >> std::get_time(&tm, format);
auto time = mktime(&tm);
auto tp = std::chrono::system_clock::from_time_t(time);
tp += duration;
time = std::chrono::system_clock::to_time_t(tp);
tm = *localtime(&time);
std::ostringstream oss;
oss << std::put_time(&tm, format);
return oss.str();
}
int main() {
auto s = "2012-12-31 23:59:00";
std::cout << increase_iso_time(s, std::chrono::minutes(20)) << std::endl;
std::cout << increase_iso_time(s, - std::chrono::hours(4)
- std::chrono::minutes(20)) << std::endl;
}
#include <ctime>
#include <cstdio>
static void delta_t(const char *otime, int delta)
{
struct tm tm1;
int n;
if ((n = sscanf(otime, "%4d-%2d-%2d %2d:%2d:%2d", &tm1.tm_year, &tm1.tm_mon, &tm1.tm_mday,
&tm1.tm_hour, &tm1.tm_min, &tm1.tm_sec)) != 6)
{
printf("%s: failed %d\n", otime, n);
return;
}
printf("%.4d-%.2d-%.2d %.2d:%.2d:%.2d\n", tm1.tm_year, tm1.tm_mon, tm1.tm_mday,
tm1.tm_hour, tm1.tm_min, tm1.tm_sec);
tm1.tm_isdst = -1;
tm1.tm_year -= 1900;
tm1.tm_mon--;
struct tm tm2 = tm1;
tm2.tm_min += delta;
struct tm tm3 = tm1;
tm3.tm_min -= delta;
mktime(&tm2);
mktime(&tm3);
char dt1[20];
char dt2[20];
char dt3[20];
strftime(dt1, sizeof(dt1), "%Y-%m-%d %H:%M:%S", &tm1);
strftime(dt2, sizeof(dt2), "%Y-%m-%d %H:%M:%S", &tm2);
strftime(dt3, sizeof(dt3), "%Y-%m-%d %H:%M:%S", &tm3);
printf("Input: %s\n", otime);
printf("Date1: %s\n", dt1);
printf("Date2: %s\n", dt2);
printf("Date3: %s\n", dt3);
}
int main(void)
{
delta_t("2010-01-25 18:02:00", 20);
delta_t("2012-12-31 23:59:00", 20);
return(0);
}
2010-01-25 18:02:00
Input: 2010-01-25 18:02:00
Date1: 2010-01-25 18:02:00
Date2: 2010-01-25 18:22:00
Date3: 2010-01-25 17:42:00
2012-12-31 23:59:00
Input: 2012-12-31 23:59:00
Date1: 2012-12-31 23:59:00
Date2: 2013-01-01 00:19:00
Date3: 2012-12-31 23:39:00