Boost之日期时间处理(date_time库)
2016-06-24 22:04
567 查看
概述
使用date_time库需要在编译时加上"-lboost_date_time",而且需要包含以下头文件:处理日期的组件:#include <boost/date_time/gregorian/gregorian.hpp>
处理时间的组件:#include <boost/date_time/posix_time/posix_time.hpp>
date类
date是date_time库处理日期的核心类,使用一个32位的整数作为内部存储,以天为单位表示时间点概念。date也全面支持比较操作和输入输入出,我们可以完全把它当成一个像int、string那样的基本类型来使用。#include <iostream> #include <boost/date_time/gregorian/gregorian.hpp> using namespace std; using namespace boost::gregorian; int main() { date d1(2001, 1, 1); date d2(2002, Feb, 2); date d3 = from_string("2003-3-3"); date d4 = from_string("2004/4/4"); date d5 = from_undelimited_string("20050505"); cout << "本地日期:" << day_clock::local_day() << endl << "UTC日期:" << day_clock::universal_day() << endl << endl; cout << "负无限日期:" << neg_infin << endl << "正无限日期:" << pos_infin << endl << "无效日期:" << not_a_date_time << endl << "最大可能日期:" << max_date_time << endl << "最小可能日期:" << min_date_time << endl << endl; cout << "对于2001-01-01:" << endl << "年:" << d1.year() << endl << "月:" << d1.month() << endl << "日:" << d1.day() << endl << endl; cout << "对于2002-02-02:" << endl << "星期数:(0表示星期天)" << d2.day_of_week() << endl << "当年的第几天:" << d2.day_of_year() << endl << "当年的第几周:" << d2.week_number() << endl << "当月的最后一天:" << d2.end_of_month() << endl << endl; cout << "对于2003-03-03:" << endl << "直接打印日期:" << d3 << endl << "使用to_simple_string打印日期:" << to_simple_string(d3) << endl << "使用to_iso_string打印日期:" << to_iso_string(d3) << endl << "使用to_iso_extended_string打印日期:" << to_iso_extended_string(d3) << endl << endl; return 0; }
输出:
本地日期:2016-Jun-24
UTC日期:2016-Jun-24
负无限日期:1
正无限日期:2
无效日期:0
最大可能日期:4
最小可能日期:3
对于2001-01-01:
年:2001
月:Jan
日:1
对于2002-02-02:
星期数:(0表示星期天)Sat
当年的第几天:33
当年的第几周:5
当月的最后一天:2002-Feb-28
对于2003-03-03:
直接打印日期:2003-Mar-03
使用to_simple_string打印日期:2003-Mar-03
使用to_iso_string打印日期:20030303
使用to_iso_extended_string打印日期:2003-03-03
date_duration类
date_duration表示日期长度,是以天为单位的时长,值可以是任意的整数,可正可负。date_time库为date_duration定义了一个常用的typedef: days。此外,date_time库还提供了months、years、weeks等另外三个时长类,分别用来表示月,年和星期,它们的含义与days类型,但行为不太相同。<span style="font-family:SimSun;">#include <iostream> #include <boost/date_time/gregorian/gregorian.hpp> using namespace std; using namespace boost::gregorian; int main() { days dd1(10), dd2(-5); cout << "dd1 + dd2 = " << (dd1 + dd2).days() << endl; weeks w(3); cout << "3个星期的天数:" << w.days() << endl; months m(5); years y(3); months m2 = y + m; cout << "3年5个月的月数:" << m2.number_of_months() << endl << endl; date d1(2001, 1, 1); date d2(2002, 1, 1); cout << "d2 - d1 = " << d2 - d1 << endl; d1 += days(10); cout << "d1 + days(10)后:" << d1 << endl; d1 += months(2); cout << "d1 + months(2)后:" << d1 << endl; d1 -= weeks(1); cout << "d1 - weeks(1)后:" << d1 << endl; d1 -= years(10); cout << "d1 - years(10)后:" << d1 << endl; return 0; }</span>
输出:
dd1 + dd2 = 5
3个星期的天数:21
3年5个月的月数:41
d2 - d1 = 365
d1 + days(10)后:2001-Jan-11
d1 + months(2)后:2001-Mar-11
d1 - weeks(1)后:2001-Mar-04
d1 - years(10)后:1991-Mar-04
date_period类
date_period类用来表示日期区间的概念,它是时间轴上一个左闭右开区间,端点是两个date对象#include <iostream> #include <boost/date_time/gregorian/gregorian.hpp> using namespace std; using namespace boost::gregorian; int main() { /* 两种构造方式 */ date_period dp1(date(2000, 1, 1), days(20)); date_period dp2(date(2000, 1, 5), date(2000, 1, 15)); /* * 成员函数begin()和last()返回日期区间的两个端点 * end()返回last()后的第一天,与标准容器中的end()含义相同 * length()返回日期区间的长度 */ cout << "dp1.begin() = " << dp1.begin() << endl << "dp1.last() = " << dp1.last() << endl << "dp1.end() = " << dp1.end() << endl << "dp1.length() = " << dp1.length() << endl << endl; /* * shift()将日期区间平移n天而长度不变 * expand()将日期区间向两端延伸n天,相当于区间长度加2n天 */ dp1.shift(days(3)); cout << "shitf(): " << dp1 << endl; dp1.expand(days(3)); cout << "expand(): " << dp1 << endl << endl; /* 判断某个日期是否在区间内或者计算日期区间的交集 */ if (dp1.is_after(date(1999, 12, 12))) cout << "dp1在1999-12-12后\n"; if (dp1.is_before(date(2000, 1, 27))) cout << "dp1在2000-01-20前\n"; if (dp1.contains(date(2000, 1, 10))) cout << "2000-01-10在dp1中\n"; if (dp1.contains(dp2)) cout << "dp1包含dp2\n"; if (dp1.intersects(dp2)) cout << "dp1和dp2存在交集,交集为:" << dp1.intersection(dp2) << endl; if (!dp1.is_adjacent(dp2)) cout << "dp1和dp2不相邻\n\n"; /* * merge()返回两个区间的并集,如果区间无交集或者不相邻则返回无效区间 * span()合并两日期区间及两者的间隔,相当于广义的merge() */ date_period dp3(date(2000, 2, 1), days(10)); cout << "dp1.merge(dp3): " << dp1.merge(dp3) << endl << "dp1.span(dp3): " << dp1.span(dp3) << endl; return 0; }
输出:
dp1.begin() = 2000-Jan-01
dp1.last() = 2000-Jan-20
dp1.end() = 2000-Jan-21
dp1.length() = 20
shitf(): [2000-Jan-04/2000-Jan-23]
expand(): [2000-Jan-01/2000-Jan-26]
dp1在1999-12-12后
dp1在2000-01-20前
2000-01-10在dp1中
dp1包含dp2
dp1和dp2存在交集,交集为:[2000-Jan-05/2000-Jan-14]
dp1和dp2不相邻
dp1.merge(dp3): [2000-Jan-01/1999-Dec-31]
dp1.span(dp3): [2000-Jan-01/2000-Feb-10]
日期迭代器
通过日期迭代器可以用简单的递增递减操作符连续访问日期,这些迭代器包括:day_iterator、week_iterator、month_iterator和year_iterator。需要注意的是它们并不符合标准迭代器的定义,没有difference_type、pointer、reference等内部类型定义,不能使用std::advance()或者operator+=来前进或者后退。#include <iostream> #include <boost/date_time/gregorian/gregorian.hpp> using namespace std; using namespace boost::gregorian; int main() { date d(2000, 1, 1); day_iterator d_iter(d); //增减步长默认为1天 ++d_iter; if (d_iter == date(2000, 1, 2)) //这里不需要解引用就可以直接比较 cout << "d_iter == date(2000, 1, 2)\n"; year_iterator y_iter(*d_iter, 8); //增减步长为8年 ++y_iter; if (y_iter->year() == 2008) cout << "增长了8年\n"; return 0; }
输出:
d_iter == date(2000, 1, 2)
增长了8年<
b4be
br />
time_duration类
与date_duration类似,date_time库使用time_duration度量时间长度。time_duration有几个子类,可以度量不同的时间分辨率,它们分别是:hours、minutes、seconds、millisec/millisecnods、microsec/microseconds和nanosec/nanoseconds。#include <iostream> #include <boost/date_time/posix_time/posix_time.hpp> using namespace std; using namespace boost::posix_time; int main() { /* 1小时10分钟30秒1毫秒 */ time_duration td1 = duration_from_string("1:10:30:001"); cout << "td1: " << td1 << endl; /* 子类 */ hours h(1); minutes m(10); seconds s(30); millisec ms(1); time_duration td2 = h + m + s + ms; cout << "td2: " << td2 << endl << "hours: " << td2.hours() << endl << "minutes: " << td2.minutes() << endl << "total_seconds: " << td2.total_seconds() << endl << "total_milliseconds: " << td2.total_milliseconds() << endl; /* 字符串表示 */ cout << "to_simple_string: " << to_simple_string(td2) << endl; //01:10:30.001000 cout << "to_iso_string: " << to_iso_string(td2) << endl; //011030.001000 return 0; }
输出:
td1: 01:10:30.001000
td2: 01:10:30.001000
hours: 1
minutes: 10
total_seconds: 4230
total_milliseconds: 4230001
to_simple_string: 01:10:30.001000
to_iso_string: 011030.001000
ptime类
ptime类表示时间点,它相当于一个日期再加上一个小于一天的时间长度。#include <iostream> #include <boost/date_time/posix_time/posix_time.hpp> #include <boost/date_time/gregorian/gregorian.hpp> using namespace std; using namespace boost::posix_time; using namespace boost::gregorian; int main() { ptime p1(date(2001, 1, 1), hours(1)); //2001年1月1日凌晨1时 ptime p2 = time_from_string("2002-2-2 02:00:00"); ptime p3 = from_iso_string("20030303T030000"); //日期与时间用字母T隔开 ptime p4 = second_clock::local_time(); //本地当前时间,秒精度 ptime p5 = microsec_clock::universal_time(); //UTC当前时间,微秒精度 cout << p1 << endl << p2 << endl << p3 << endl << p4 << endl << p5 << endl << endl; /* * date()获得时间点中的日期 * time_of_day()获得时间长度 */ date d = p1.date(); time_duration td = p1.time_of_day(); cout << d << ", " << td << endl << endl; cout << to_simple_string(p2) << endl //转换为YYYY-mmm-DD HH:MM:SS.ffffff << to_iso_string(p2) << endl //转换为YYYYMMDDTHHMMSS,ffffff << to_iso_extended_string(p2) << endl; //转换为YYYY-MM-DDTHH:MM:SS,ffffff return 0; }
输出:
2001-Jan-01 01:00:00
2002-Feb-02 02:00:00
2003-Mar-03 03:00:00
2016-Jun-26 15:35:23
2016-Jun-26 07:35:23.240536
2001-Jan-01, 01:00:00
2002-Feb-02 02:00:00
20020202T020000
2002-02-02T02:00:00
time_period类
与日期区间date_period对应,date_time库也有时间区间的概念,类time_period使用ptime作为区间的两个端点,同样是左闭右开区间,它与date_period用法基本相同。#include <iostream> #include <boost/date_time/posix_time/posix_time.hpp> #include <boost/date_time/gregorian/gregorian.hpp> using namespace std; using namespace boost::posix_time; using namespace boost::gregorian; int main() { ptime p(date(2014,1,1),hours(12)) ; time_period tp1(p, hours(8)); //一个8小时的区间 time_period tp2(p + hours(8), hours(1)); //1小时的区间 if (tp1.end() == tp2.begin() && tp1.is_adjacent(tp2)) cout << "两个区间相邻\n"; if (!tp1.intersects(tp2)) cout << "两个区间不相交\n"; tp1.shift(hours(1)); //平移1小时 if (tp1.is_after(p)) cout << "tp1在中午之后\n"; if (tp1.intersects(tp2)) cout << "两个区间现在相交\n"; tp2.expand(hours(10)); //向两端扩展10小时 if (tp2.contains(p) && tp2.contains(tp1)) cout << "tp2包含p且包含tp1\n"; return 0; }
输出:
两个区间相邻
两个区间不相交
tp1在中午之后
两个区间现在相交
tp2包含p且包含tp1
时间迭代器
不同于日期迭代器,时间迭代器只有一个time_iterator。它在构造时传入一个起始时间点ptime对象和一个步长time_duration对象,然后就同日期迭代器一样使用前置式operator++、operator--来递增或递减时间,解引用操作符返回一个ptime对象。#include <iostream> #include <boost/date_time/posix_time/posix_time.hpp> #include <boost/date_time/gregorian/gregorian.hpp> using namespace std; using namespace boost::posix_time; using namespace boost::gregorian; int main() { ptime p(date(2014,11,3),hours(10)) ; for (time_iterator t_iter(p, minutes(10)); t_iter < p + hours(1); ++ t_iter) cout << *t_iter << endl; return 0; }
输出:
2014-Nov-03 10:00:00
2014-Nov-03 10:10:00
2014-Nov-03 10:20:00
2014-Nov-03 10:30:00
2014-Nov-03 10:40:00
2014-Nov-03 10:50:00
相关文章推荐
- boost相关小知识(长期顶置更新)
- C++单元测试:boost.test
- boost asio学习笔记 [1] - 同步通讯
- boost_asio学习笔记[2] - 客户端异步通讯
- boost::flat_map性能测试
- Ubuntu下如何安装boost?
- How to get a boost::shared_ptr from this
- boost 库 enable_shared_from_this 实现原理分析
- boost bind使用指南
- 最常用的两种C++序列化方案的使用心得
- 使用boost进行CRC64计算
- [网络开发]boost::asio简介
- Windows下如何编译使用boost?
- Boost库学习(0)
- Boost库学习(1)log和unittest
- Boost库学习(2)thread 1
- Boost库学习(3)thread 2
- Boost库学习(4)thread 3
- Boost库学习(6)filesystem
- Boost库学习(7)regex