MySQL week()函数详解

一枚小产品的学习记录

在做sql练习题时了解到的新函数,做个简要的记录,因非技术人员(专业人士),可能会存在一定的局限性,若有不严谨的地方,请指正。

在日常的业务统计需求中,可能会有类似查询“某一日是今年第几周“的需求。mysql提供了week(date,mode)函数来满足此种需求。
其中2个参数分别为:

date:date是要获取周数的日期,比如2020-01-04,记得要加引号,若不加引号也不会报错,会返回null。

mode: mode是计算逻辑的参数,用于确定周数计算的逻辑。看了众多资料,统一认定mode的参数为0到7这8个参数,也就是8种计算逻辑。
但是我尝试了8-15也不会报错,且返回了合理的值,经个人多次验证及推测,底层会将mode对8取模。最终的mode参数为mod(mode,8) 。备注:本人的mysql为8.0.21版本。
mode可不写,其默认参数为:0, 可通过设置全局变量来修改该值。

至于为何要有mode这个参数呢,我想主要是为了符合各种统计逻辑的需求,因为按照不同的计算逻辑,特定的某一天会属于不同的周。
举2个最简单的例子:
1;有些人把周日当成一周的第一天,有些人把周一当成一周的第一天。
2:有些人把新年的第一个周日到第二个周日算作新年的第一周,不会去考虑其他因素。
有些人则认为从1月1日起到下一个周日的天数若大于3天则这几天算为一周,若小于3天则这几天算为第0周,或者这
几天算作去年的最后一周。

所以可以看出因为计算逻辑的不统一,会造成统计误差。
因此mysql提供了8种计算逻辑,来满足各种统计需求。
下表为各种模式的具体解释:


image.png

那么我以2021年1月2日举下例子:
日历如下:

image.png

测试如下:

SELECT WEEK('2021-01-02',0)           #运行结果:0
SELECT WEEK('2021-01-02',1)           #运行结果:0
SELECT WEEK('2021-01-02',2)           #运行结果:52
SELECT WEEK('2021-01-02',3)           #运行结果:53

当模式为0时,对照模式表可以得知其计算逻辑是:把星期日当做一周的第一天,且第一周是以2021年的第一个星期日开始的,且在2021年的第一个星期日前那些属于2021年的天数都归为第0周。而2021年1月2日是2021年第一个星期日之前的日期,所以返回的结果是0。

当模式为1时,对照模式表可以得知其计算逻辑是:把星期一当做一周的第一天,且1月1日到本年第一个周一的天数超过3天,则认定这几天处于本年的第1周,若天数没超过3天(不足4天),则认定这几天处于本年的第0周。而2021年1月1日到第一个周一(2021年1月4日)只有3天(即1月1日、1月2日、1月3日)。所以认定这几天属于2021年的第0周,所以返回的结果为0。

当模式为2时,对照模式表可以得知其计算逻辑是:把星期日当做一周的第一天,且第一周是以2021年的第一个星期日开始的,前面的日期都算作上年度的最后一周(而模式0则是把这几天算作为第0周)。而2021年1月2日是2021年第一个星期日之前日期,所以认定这几天属于2020年的最后一周(2020年的第52周),所以返回的结果为52。备注也就是说2020年的日期也是默认使用2这种模式来计算的。

其他的模式就不做详细说明了,大家自己去验证吧~

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。
禁止转载,如需转载请通过简信或评论联系作者。

推荐阅读更多精彩内容