MySQL 获取上个月的具体日期
MySQL get specific date of last month
我想 select 自上个月 20th
以来的所有行。
我知道我可以使用 SELECT NOW() - INTERVAL 1 MONTH
select 一个月前的日期,但我如何设置那个月的特定日期?
今天是 March 28th
,我想 select 所有比 February 20th
新的行。
即使我可以直接设置日期,如果查询的日期是 31st
那对 2 月不起作用,而应该 select 该月的最后一天。
注意:20th 只是一个示例,该值是在代码的其他地方动态生成的。
一些例子:
Day: 20th each month
Now: March 28th | Query: February 20th
Now: May 28th | Query: April 20th
Day: 31st each month
Now: March 28th | Query: February 28th // we select last day instead of 31st
Now: May 28th | Query: April 30th // we select last day instead of 31st
完整的查询类似于 SELECT * FROM sales WHERE date > SET_DAY(20, NOW() - INTERVAL 1 MONTH)
。
那么,我可以将 SET_DAY
替换为什么(也适用于较短的月份)?
一个非常常见的用例是计费周期,您想要select当前计费周期内的所有数据。
好吧,我相信这可以解决问题
select now()
- interval 1 month
- interval(
day(now())
- least(
20,
day(last_day(now() - interval 1 month))
)
) day
假设您在客户端中有一个参数是目标天数,并且您想在 sql 中验证它(确保您想出上个月内的一天),而不是客户,我会做:
least(
date(date_format(current_date - interval 1 month, '%Y-%m-01')) + interval ? - 1 day,
date(date_format(current_date, '%Y-%m-01')) - interval 1 day
)
一个警告:current_date 将是连接时区中的当前日期,由客户端控制;如果我知道我希望当天在哪个时区,我更愿意始终明确,例如:
date(convert_tz(utc_timestamp(), '+00:00', 'America/Los_Angeles'))
而不只是 current_date(两个地方)。
我刚刚意识到我的问题并没有包括所有情况。如果最后一个账单日在本月内,则应计算本月的 20 日(而不是之前的)。
根据@ysth 的回答,我在本月的 select 20 日添加了一个 IF(如果我们通过了),否则上个月:
IF(DAY(current_date) >= 20,
date(date_format(current_date, '%Y-%m-01')) + interval 20 - 1 day,
least(
date(date_format(current_date - interval 1 month, '%Y-%m-01')) + interval 20 - 1 day,
date(date_format(current_date, '%Y-%m-01')) - interval 1 day
)
);
我想 select 自上个月 20th
以来的所有行。
我知道我可以使用 SELECT NOW() - INTERVAL 1 MONTH
select 一个月前的日期,但我如何设置那个月的特定日期?
今天是 March 28th
,我想 select 所有比 February 20th
新的行。
即使我可以直接设置日期,如果查询的日期是 31st
那对 2 月不起作用,而应该 select 该月的最后一天。
注意:20th 只是一个示例,该值是在代码的其他地方动态生成的。
一些例子:
Day: 20th each month
Now: March 28th | Query: February 20th
Now: May 28th | Query: April 20th
Day: 31st each month
Now: March 28th | Query: February 28th // we select last day instead of 31st
Now: May 28th | Query: April 30th // we select last day instead of 31st
完整的查询类似于 SELECT * FROM sales WHERE date > SET_DAY(20, NOW() - INTERVAL 1 MONTH)
。
那么,我可以将 SET_DAY
替换为什么(也适用于较短的月份)?
一个非常常见的用例是计费周期,您想要select当前计费周期内的所有数据。
好吧,我相信这可以解决问题
select now()
- interval 1 month
- interval(
day(now())
- least(
20,
day(last_day(now() - interval 1 month))
)
) day
假设您在客户端中有一个参数是目标天数,并且您想在 sql 中验证它(确保您想出上个月内的一天),而不是客户,我会做:
least(
date(date_format(current_date - interval 1 month, '%Y-%m-01')) + interval ? - 1 day,
date(date_format(current_date, '%Y-%m-01')) - interval 1 day
)
一个警告:current_date 将是连接时区中的当前日期,由客户端控制;如果我知道我希望当天在哪个时区,我更愿意始终明确,例如:
date(convert_tz(utc_timestamp(), '+00:00', 'America/Los_Angeles'))
而不只是 current_date(两个地方)。
我刚刚意识到我的问题并没有包括所有情况。如果最后一个账单日在本月内,则应计算本月的 20 日(而不是之前的)。
根据@ysth 的回答,我在本月的 select 20 日添加了一个 IF(如果我们通过了),否则上个月:
IF(DAY(current_date) >= 20,
date(date_format(current_date, '%Y-%m-01')) + interval 20 - 1 day,
least(
date(date_format(current_date - interval 1 month, '%Y-%m-01')) + interval 20 - 1 day,
date(date_format(current_date, '%Y-%m-01')) - interval 1 day
)
);