关于夏令时,UTC,GMT这几个概念建议先简单了解下,下面不做解释
先丢结论以表诚意:
如果程序不需要考虑时区,夏令时或者将来数据库的机子迁移到别的地方时区变化,用datetime类型比较方便;
用timestamp可以避免上述的问题(mysql官方文档的简单解释是数据存入timestamp时会根据时区转换为UTC时间,取出的时候做个反转换),但众所周知timestamp的存储位数只有4个字节,只能用到2037年;
如果程序要避免第一个问题,同时要跑到2037之后,可以用int或bigint存储。此时需要一些mysql的转换函数处理展示问题。
参考链接:
https://zh.wikipedia.org/wiki/%E5%A4%8F%E6%97%B6%E5%88%B6
http://billauer.co.il/blog/2009/03/mysql-datetime-epoch-unix-time/
http://stackoverflow.com/questions/9148195/what-datatype-should-i-use-to-store-time-in-mysql-for-my-application
http://dev.mysql.com/doc/refman/5.7/en/datetime.html
先丢结论以表诚意:
如果程序不需要考虑时区,夏令时或者将来数据库的机子迁移到别的地方时区变化,用datetime类型比较方便;
用timestamp可以避免上述的问题(mysql官方文档的简单解释是数据存入timestamp时会根据时区转换为UTC时间,取出的时候做个反转换),但众所周知timestamp的存储位数只有4个字节,只能用到2037年;
如果程序要避免第一个问题,同时要跑到2037之后,可以用int或bigint存储。此时需要一些mysql的转换函数处理展示问题。
自己另外测试了下用datetime和int存储时间在查询方面的效率是不是有差别
mysql官方的reference里说datetime本质上存的也是int,所以我的理解应该差别不大
表结构如上所示,tablec用int存储,tabled用datetime,字段createTime都做了索引两个表大概都是27万的数据 执行如下sql查询时间非常接近,在我机子上大概都是5秒多CREATE TABLE `tablec` ( `id` INT(11) NOT NULL AUTO_INCREMENT, `createTime` INT(32) NOT NULL DEFAULT '0', PRIMARY KEY (`id`), INDEX `createTime` (`createTime`) ) COLLATE='utf8_general_ci' ENGINE=InnoDB
CREATE TABLE `tabled` ( `id` INT(11) NOT NULL AUTO_INCREMENT, `createTime` DATETIME NOT NULL DEFAULT '0000-00-00 00:00:00', PRIMARY KEY (`id`), INDEX `createTime` (`createTime`) ) COLLATE='utf8_general_ci' ENGINE=InnoDB
select count(*) from tableC t where t.createTime >= unix_timestamp('2011-01-09 00:22:33') and t.createTime <= unix_timestamp('2017-10-27 00:22:33');
select count(*) from tableD t where t.createTime between '2011-01-09 00:22:33' and '2017-10-27 00:22:33';
参考链接:
https://zh.wikipedia.org/wiki/%E5%A4%8F%E6%97%B6%E5%88%B6
http://billauer.co.il/blog/2009/03/mysql-datetime-epoch-unix-time/
http://stackoverflow.com/questions/9148195/what-datatype-should-i-use-to-store-time-in-mysql-for-my-application
http://dev.mysql.com/doc/refman/5.7/en/datetime.html