经常会有人被strtotime结合-1 month, +1 month, next month的时候搞得很困惑, 然后就会觉得这个函数有点不那么靠谱, 动不动就出问题. 用的时候就会很慌…

这不, 刚刚就有人在微博上又问我:

鸟哥,今天是2018-07-31 执行代码:

date("Y-m-d",strtotime("-1 month"))

怎么输出是2018-07-01?

好的吧, 虽然这个问题看起来很迷惑, 但从内部逻辑上来说呢, 其实是”对”的, 你先别着急哈, 让我慢慢讲:

我们来模拟下date内部的对于这种事情的处理逻辑:

1. 先做-1 month, 那么当前是07-31, 减去一以后就是06-31.

2. 再做日期规范化, 因为6月没有31号, 所以就好像2点60等于3点一样, 6月31就等于了7月1

是不是逻辑很”清晰”呢? 我们也可以手动验证第二个步骤, 比如:

var_dump(date("Y-m-d", strtotime("2017-06-31")));

//输出2017-07-01

也就是说, 只要涉及到大小月的最后一天, 都可能会有这个迷惑, 我们也可以很轻松的验证类似的其他月份, 印证这个结论:

var_dump(date("Y-m-d", strtotime("-1 month", strtotime("2017-03-31"))));

//输出2017-03-03

var_dump(date("Y-m-d", strtotime("+1 month", strtotime("2017-08-31"))));

//输出2017-10-01

var_dump(date("Y-m-d", strtotime("next month", strtotime("2017-01-31"))));

//输出2017-03-03

var_dump(date("Y-m-d", strtotime("last month", strtotime("2017-03-31"))));

//输出2017-03-03

那怎么办呢?

从PHP5.3开始呢, date新增了一系列修正短语, 来明确这个问题, 那就是”first day of” 和 “last day of”, 也就是你可以限定好不要让date自动”规范化”:

var_dump(date("Y-m-d", strtotime("last day of -1 month", strtotime("2017-03-31"))));

//输出2017-02-28

var_dump(date("Y-m-d", strtotime("first day of +1 month", strtotime("2017-08-31"))));

输出2017-09-01

var_dump(date("Y-m-d", strtotime("first day of next month", strtotime("2017-01-31"))));

输出2017-02-01

var_dump(date("Y-m-d", strtotime("last day of last month", strtotime("2017-03-31"))));

输出2017-02-28

那如果是5.3之前的版本(还有人用么?), 你可以使用mktime之类的, 把所有的日子忽略掉, 比如都限定为每月1号就可以了, 只不过就不如直接用first day来的更加优雅.

现在, 搞清楚了内部原理, 是不是就不慌了?

php语法难看,PHP语法之令人困惑的strtotime相关推荐

  1. Java中语法分析器_语法分析器(java语法分析器)

    亲这是一款采用递归下降语法分析器,是一种适合手写语法编译器的方法,且非常简单.递归下降法对语言所用的文法有一些限制,但递归下降是现阶段主流的语法分析方法,因为它可以由开发人员高度控制,在提供错误信息方 ...

  2. java语法分析_语法分析器(java语法分析器)

    亲这是一款采用递归下降语法分析器,是一种适合手写语法编译器的方法,且非常简单.递归下降法对语言所用的文法有一些限制,但递归下降是现阶段主流的语法分析方法,因为它可以由开发人员高度控制,在提供错误信息方 ...

  3. 爬虫之xpath语法-节点修饰语法

    爬虫之xpath语法-节点修饰语法 可以根据标签的属性值.下标等来获取特定的节点 1.1 节点修饰语法    [用[ ]方括号修饰标签或节点] 1.2 关于xpath的下标 在xpath中,第一个元素 ...

  4. 几个有趣的名词--语法糖、语法盐等

    今天看<Java NIO>,里边出现"语法糖"这一名词,觉得挺有趣就问google,结果出来连带了其他几个类似名词,这里仅作整理. 语法糖 语法糖(Syntactic ...

  5. 【计算理论】上下文无关语法 ( 语法组成 | 规则 | 语法 | 语法示例 | 约定的简写形式 | 语法分析树 )

    文章目录 I . 语法组成 II . 规则 III . 语法 IV . 语法示例 V . 语法简写形式 VI . 语法分析树 VII . 代数表达式 语法 I . 语法组成 上下文无关语法 组成 : ...

  6. 如何让 zend studio 10 识别 Phalcon语法并且进行语法提示

    让 zend studio 10 识别 Phalcon语法并且进行语法提示 https://github.com/rogerthomas84/PhalconPHPDoc 下载解压后,把里面 phalc ...

  7. [PHP语法]PHP基础语法与数据类型

    基础语法: php是一门弱类型编程语言 在.php文件中php代码需要包含在<?php 和 ?> 之间,html可以和php混合编写 语句必须以;分号结束 变量名前面必须包含$,变量名可以 ...

  8. oauth2和jwt_OAuth2,JWT,Open-ID Connect和其他令人困惑的事物

    oauth2和jwt 免责声明 如果觉得我必须从一个重要的免责声明开始这篇文章: 不要太相信我要说的话. 我之所以这样说,是因为我们正在讨论安全性. 而且, 当您谈论安全性时,除了100%正确的陈述外 ...

  9. OAuth2,JWT,Open-ID Connect和其他令人困惑的事物

    免责声明 如果觉得我必须从一个重要的免责声明开始这篇文章: 不要太相信我要说的话. 我之所以这样说,是因为我们正在讨论安全性. 而且, 当您谈论安全性时,除了100%正确的陈述外,还有冒任何其他风险的 ...

最新文章

  1. 计算机不能启动 如何排除故障,开工发现电脑无法开机 如何排查故障?
  2. 《基于Windows 7特性的程序开发系列》视频分享
  3. Java.io包中常用的类
  4. hbase的gui工具调研
  5. pytorch resnet50_用Pytorch手工实现ResNet50
  6. 解压并安装protobuf库_golang-leaf服务器-protobuf的安装
  7. html jsf ajax blur,是否可以使用JSF ajax更新非JSF组件(纯HTML)?
  8. 无需充电的太阳能汽车有多强?约17万起,续航高达1609km
  9. 在vue的项目中引入swiper插件
  10. 自己写好记的Oracle的 Group By 、 Group By Rollup和Group By Cube基础
  11. Unity 插件之 Highlighting 高亮插件
  12. 根据标题自动生成图片程序,使用教程,并附程序下载
  13. 教程篇(7.0) 11. FortiGate安全 入侵防御和拒绝服务 ❀ Fortinet 网络安全专家 NSE 4
  14. 二次函数图像如何用计算机绘制,如何快速画二次函数图像
  15. window7调用计算机,教你查看win7系统电脑使用记录的具体方法
  16. 阿里云ACE备考题库161-240
  17. 理解async与await
  18. window7 下调试PTAM,PTAMM
  19. 信息泄露能算高危漏洞吗
  20. 笔记本固态硬盘温度测试软件,固态硬盘散热测试

热门文章

  1. 【Week9作业 B】东东学打牌【模拟】
  2. flashloader
  3. android 注解和反射 (入门以及使用)
  4. OSCAR开源大会 | 「开源学」:如何分门别类理解开源
  5. java中MVC原理详解,Spring MVC 原理总结
  6. 淘客外卖返利系统,外卖cps系统 ,社群团购系统
  7. Invalid bound statement 无效的绑定 的解决办法!
  8. C语言二维数组内存申请及初始化方法
  9. java.lang.NoSuchMethodException: com.gql.pojo.User.init() 解决方案
  10. 2014 ChinaJoy落下帷幕 十大年度热门事件盘点