日期 & 时间
有四个与时间相关的类型:clock_t、time_t、size_t 和 tm。类型 clock_t、size_t 和 time_t 能够把系统时间和日期表示为某种整数。结构类型 tm 把日期和时间以 C 结构的形式保存,tm 结构的定义如下:
struct tm {
int tm_sec; // 秒,正常范围从 0 到 59,但允许至 61
int tm_min; // 分,范围从 0 到 59
int tm_hour; // 小时,范围从 0 到 23
int tm_mday; // 一月中的第几天,范围从 1 到 31
int tm_mon; // 月,范围从 0 到 11
int tm_year; // 自 1900 年起的年数
int tm_wday; // 一周中的第几天,范围从 0 到 6,从星期日算起
int tm_yday; // 一年中的第几天,范围从 0 到 365,从 1 月 1 日算起
int tm_isdst; // 夏令时
}
使用日期和时间相关的函数和结构,需要在 C++ 程序中引用 <ctime> 头文件。 C++ 标准库中操作日期和时间的函数:
函数 | 描述 |
time_t time(time_t *t) | 返回时间戳, 若参数 *t不为空,将返回值也存储在指针 t 指向的内存空间,若当前系统没有时间,返回-1 |
char *ctime(const time_t *timer) | 返回一个表示当地时间的字符串,当地时间是基于参数 timer。返回的字符串格式如下: Www Mmm dd hh:mm:ss yyyy 其中,Www 表示星期几,Mmm 是以字母表示的月份,dd 表示一月中的第几天,hh:mm:ss 表示时间,yyyy 表示年份。 |
struct tm *localtime(const time_t *timer) | 使用 timer 的值来填充 tm 结构。timer 的值被分解为 tm 结构,并用本地时区表示。 |
clock_t clock(void) | 返回自程序启动起,处理器时钟所使用的时间。如果失败,则返回 -1 值。 |
char *asctime(const struct tm *timeptr) | 返回一个 C 字符串,包含了可读格式的日期和时间信息 Www Mmm dd hh:mm:ss yyyy,其中,Www 表示星期几,Mmm 是以字母表示的月份,dd 表示一月中的第几天,hh:mm:ss 表示时间,yyyy 表示年份。 |
struct tm *gmtime(const time_t *timer) | 该函数返回一个指向 time 的指针,time 为 tm 结构,用协调世界时(UTC)也被称为格林尼治标准时间(GMT)表示。 |
time_t mktime(struct tm *timeptr) | 返回一个 time_t 值,该值对应于以参数传递的日历时间。如果发生错误,则返回 -1 值。 |
double difftime(time_t time1, time_t time2) | 返回以双精度浮点型 double 值表示的两个时间之间相差的秒数 (time1 - time2) |
size_t strftime(char *str, size_t maxsize, const char *format, const struct tm *timeptr) | 根据 format 中定义的格式化规则,格式化结构 timeptr 表示的时间,并把它存储在 str 中。如果产生的 C 字符串小于 size 个字符(包括空结束字符),则会返回复制到 str 中的字符总数(不包括空结束字符),否则返回零。 |
当前日期&时间 和 tm 格式化时间
#include <iostream>
#include <ctime>
using namespace std;
int main( )
{
// 基于当前系统的当前日期/时间
time_t now = time(0);
// 把 now 转换为字符串形式
char* dt = ctime(&now);
cout << "本地日期和时间:" << dt << endl;
// 把 now 转换为 tm 结构
tm *gmtm = gmtime(&now);
dt = asctime(gmtm);
cout << "UTC 日期和时间:"<< dt << endl;
// 输出 tm 结构的各个组成部分
cout << "年: "<< 1900 + gmtm->tm_year << endl;
cout << "月: "<< 1 + gmtm->tm_mon<< endl;
cout << "日: "<< gmtm->tm_mday << endl;
cout << "时间: "<< gmtm->tm_hour << ":";
cout << gmtm->tm_min << ":";
cout << gmtm->tm_sec << endl;
}
tm 结构在 C/C++ 中处理日期和时间相关的操作时,显得尤为重要。箭头 -> 运算符来访问结构成员。
输入&输出
C++ 的 I/O 发生在流中,流是字节序列。如果字节流是从设备(如键盘、磁盘驱动器、网络连接等)流向内存,这叫做输入操作。如果字节流是从内存流向设备(如显示屏、打印机、磁盘驱动器、网络连接等),这叫做输出操作。
I/O 库头文件
头文件 | 描述 |
<iostream> | 该文件定义了 cin(标准输入流)、cout(标准输出流)、cerr (非缓冲标准错误流)和 clog (缓冲标准错误流)对象 |
<iomanip> | 该文件通过所谓的参数化的流操纵器(比如 setw 和 setprecision),来声明对执行标准化 I/O 有用的服务 |
<fstream> | 该文件为用户控制的文件处理声明服务 |
标准输入流 cin
预定义的对象 cin 是 iostream 类的一个实例。cin 对象附属到标准输入设备,通常是键盘。cin 是与流提取运算符 >> 结合使用的,流提取运算符 >> 在一个语句中可以多次使用
C++ 编译器根据要输入值的数据类型,选择合适的流提取运算符来提取值,并把它存储在给定的变量中。
标准输出流 cout
预定义的对象 cout 是 iostream 类的一个实例。cout 对象"连接"到标准输出设备,通常是显示屏。cout 是与流插入运算符 << 结合使用的,流插入运算符 << 在一个语句中可以多次使用。
C++ 编译器根据要输出变量的数据类型,选择合适的流插入运算符来显示值。<< 运算符被重载来输出内置类型(整型、浮点型、double 型、字符串和指针)的数据项。
输出流中的函数(模板):
#include <iostream>
#include <iomanip>
using namespace std;
int main()
{
cout<<setiosflags(ios::left|ios::showpoint); // 设左对齐,以一般实数方式显示
cout.precision(5); // 设置除小数点外有五位有效数字
cout<<123.456789<<endl;
cout.width(10); // 设置显示域宽10
cout.fill('*'); // 在显示区域空白处用*填充
cout<<resetiosflags(ios::left); // 清除状态左对齐
cout<<setiosflags(ios::right); // 设置右对齐
cout<<123.456789<<endl;
cout<<setiosflags(ios::left|ios::fixed); // 设左对齐,以固定小数位显示
cout.precision(3); // 设置实数显示三位小数
cout<<999.123456<<endl;
cout<<resetiosflags(ios::left|ios::fixed); //清除状态左对齐和定点格式
cout<<setiosflags(ios::left|ios::scientific); //设置左对齐,以科学技术法显示
cout.precision(3); //设置保留三位小数
cout<<123.45678<<endl;
return 0;
}
其中 cout.setf 跟 setiosflags 一样,cout.precision 跟 setprecision 一样,cout.unsetf 跟 resetiosflags 一样。
setiosflags(ios::fixed) 固定的浮点显示
setiosflags(ios::scientific) 指数表示
setiosflags(ios::left) 左对齐
setiosflags(ios::right) 右对齐
setiosflags(ios::skipws 忽略前导空白
setiosflags(ios::uppercase) 16进制数大写输出
setiosflags(ios::lowercase) 16进制小写输出
setiosflags(ios::showpoint) 强制显示小数点
setiosflags(ios::showpos) 强制显示符号
cout.setf 常见的标志:
标志 | 功能 |
---|---|
boolalpha | 可以使用单词”true”和”false”进行输入/输出的布尔值. |
oct | 用八进制格式显示数值. |
dec | 用十进制格式显示数值. |
hex | 用十六进制格式显示数值. |
left | 输出调整为左对齐. |
right | 输出调整为右对齐. |
scientific | 用科学记数法显示浮点数. |
fixed | 用正常的记数方法显示浮点数(与科学计数法相对应). |
showbase | 输出时显示所有数值的基数. |
showpoint | 显示小数点和额外的零,即使不需要. |
showpos | 在非负数值前面显示”+(正号)”. |
skipws | 当从一个流进行读取时,跳过空白字符(spaces, tabs, newlines). |
unitbuf | 在每次插入以后,清空缓冲区. |
internal | 将填充字符回到符号和数值之间. |
uppercase | 以大写的形式显示科学记数法中的”e”和十六进制格式的”x”. |
非缓冲标准错误流 cerr
预定义的对象 cerr 是 iostream 类的一个实例。cerr 对象附属到标准错误设备,通常也是显示屏,但是 cerr 对象是非缓冲的,且每个流插入到 cerr 都会立即输出。cerr 也是与流插入运算符 << 结合使用的
缓冲标准错误流 clog
预定义的对象 clog 是 iostream 类的一个实例。clog 对象附属到标准错误设备,通常也是显示屏,但是 clog 对象是缓冲的。这意味着每个流插入到 clog 都会先存储在缓冲在,直到缓冲填满或者缓冲区刷新时才会输出。clog 也是与流插入运算符 << 结合使用的
所以,使用 cerr 流来显示错误消息,而其他的日志消息则使用 clog 流来输出。