mysql按某列计数_Mysql按条件计数的几种方法
最近在给某网站的后台添加一系列的统计功能,遇到很多需要按条件计数的情况。尝试了几种方法,下面简要记录,供大家参考。
问题描述
为使讨论简单易懂,我将问题稍作简化,去掉诸多的背景。
从前有一个皇帝,他有50个妃子,这些妃子很没有天理的给他生了100,000个儿子,于是,皇帝很苦恼,海量的儿子很难管理,而且,他想知道每个妃子给他生了多少个儿子,从而论功行赏,这很难办。于是,皇帝请了一个程序员帮他编了一个程序,用数据库来存储所有的儿子的信息,这样就可以用程序来统计和管理啦。
数据库的结构如下:
id
皇子的唯一编号
mother
皇子母亲的唯一编号
皇帝把妃子分成了两个等级,天宫娘娘(编号小于25)和地宫娘娘(编号大于等于25),他想知道天宫娘娘们和地宫娘娘们的生育能力孰强孰弱。于是,程序员开始写SQL Query了。
方法1:使用GROUP BY
SQL Query
SELECT COUNT(*) FROM `prince` GROUP BY `mother` > 24;
执行结果
count(*)
50029
49971
在100,000行数据上的运行时间:0.0335 秒
分析
这种GROUP BY方法的最大问题在于:无法区分所得到的结果。这两个数字哪一个是天宫娘娘们所生的皇子数,哪一个是地宫娘娘们所生的皇子数呢?不知道。所以,尽管它统计出了总数,但是没有什么意义。
因此,为了区分统计结果,必须要把条件 mother > 24 也作为一个字段在结果集中作为一个字段体现出来,修改后的sql如下:
SELECT COUNT(*) AS `number`, `mother` > 24 AS `type` FROM `prince` GROUP BY `mother` > 24;
执行结果
number type
50029 0
49971 1
条件表达式作为字段时,该字段的值就是该条件表达式的值,因此,对应我们的例子,type = 1 也就是表示 mother > 24 的值为1,因此,第二行中的数字代表地宫娘娘们所生的皇子数。
经过修改后,我们看出,天宫娘娘们略胜一筹。
优缺点
缺点是显而易见的,由于使用了条件表达式作为分组依据,它只能做二元的划分,对于要分成多类进行统计的情况不能够胜任。比如要分别统计1~10号、11~24号,25号~50号妃子的产子数,就无法实现了。
另外,由于使用了GROUP BY,因此涉及到排序,执行时间上要更长。
我暂时没有发现这种方法的优点。
方法2:使用嵌套的SELECT
使用嵌套的SELECT也可以达到目的,在每个SELECT子句中统计一个条件下的数据,然后用一个主SELECT把这些统计数据整合起来。
SQL Query
SELECT
( SELECT COUNT( * ) FROM `prince` WHERE `mother` >24 ) AS `digong`,
( SELECT COUNT( * ) FROM `prince` WHERE `mother` <=24 ) AS `tiangong`
执行结果
digong tiangong
49971 50029
在100,000行数据上的运行时间:0.0216 秒
分析
这种嵌套SELECT的方法非常直观,就是分别统计各个条件下的数值,最后进行汇总,通俗易懂,跟自然语言没啥区别了。
优缺点
优点就是直观,而且速度也比GROUP BY要快。虽然是3条SELECT语句,看起来比GROUP BY的方案多了2条语句,但是它不涉及到排序,这就节省了很多时间。
缺点可能就是语句稍多,对语句数量有洁癖的同学可能会比较不舒服。
方法3:使用CASE WHEN
CASE WHEN语句的功能很强大,可以定义灵活的查询条件,很适合进行分类统计。
SQL Query
SELECT
COUNT( CASE WHEN `mother` >24 THEN 1 ELSE NULL END ) AS `digong`,
COUNT( CASE WHEN `mother` <=24 THEN 1 ELSE NULL END ) AS `tiangong`
FROM prince
执行结果
digong tiangong
49971 50029
在100,000行数据上的运行时间:0.02365825 秒
分析
此方法的关键在于
COUNT( CASE WHEN `mother` >24 THEN 1 ELSE NULL END )
这里的COUNT和CASE WHEN联合使用,做到了分类计数。先使用CASE WHEN,当满足条件时,将字段值设置为 1, 不满足条件时,将字段值设置为NULL,接着COUNT函数仅对非NULL字段进行计数,于是,问题解决。
优缺点
优点嘛,此方法也不涉及到排序,因此运行时间上与方法2相当,SELECT语句减少到了 1 条。
缺点就是语句比较长,对语句长度有洁癖的同学可能会比较不舒服。
总结
对于确定分类的按条件计数,可以尽量不用GROUP BY,从而避免排序动作,加速Query的执行。
如果需要根据某个字段的值进行分类,而该字段的值是可变的,比如皇帝要统计每一个妃子的产子数,而他可能不停的再娶很多妃子,这种情况下,使用方法2和方法3就不太灵光了,还是使用一个GROUP BY来得简单便捷。
mysql按某列计数_Mysql按条件计数的几种方法相关推荐
- mysql 增加字段位置靠前_mysql 字段指定值靠前排序方法,多字段排序排序方法
背景:SEO下选择某查询条件 查询展示信息为装修设计师以及设计师作品.设计师原型设计为:选择某风格 例如:简约,则列表出现拥有简约风格的设计师信息以及该设计师类型为简约的作品(3条靠前记录) 浏览原型 ...
- excil mysql查询 条件_excel多条件查找 Excel中实现多条件查找的15种方法
excel多条件查找 Excel中实现多条件查找的15种方法,平凡的世界平凡的你,努力学习使我们变得不平凡,今天要介绍的知识是excel多条件查找的相关知识,你准备好学习excel多条件查找 Exce ...
- react把表格渲染好ui_在React中实现条件渲染的7种方法
借助react,我们可以构建动态且高度交互的单页应用程序,充分利用这种交互性的一种方法是通过条件渲染. 条件渲染一词描述了根据某些条件渲染不同UI标签的能力.在react文档中,这是一种根据条件渲染不 ...
- Mysql使用binlog恢复数据解决误操作问题的两种方法
Mysql使用binlog恢复数据解决误操作问题的两种方法 参考文章: (1)Mysql使用binlog恢复数据解决误操作问题的两种方法 (2)https://www.cnblogs.com/Data ...
- 如何让表格中的一列按照公式计算机,excel设置一列运用相同类型的公式的两种方法...
腾讯视频/爱奇艺/优酷/外卖 充值4折起 EXCEL工作表中同一列运用相同类型的公式,如图中所示,A1*B1,积要显示在C1,在C1单元格输入公式,=A1*B1按回车,积就显示在C1了,若往下整个C列 ...
- mysql如何把列转行_mysql列转行的技巧(分享)
前言: 由于很多业务表因为历史原因或者性能原因,都使用了违反第一范式的设计模式.即同一个列中存储了多个属性值(具体结构见下表). 这种模式下,应用常常需要将这个列依据分隔符进行分割,并得到列转行的结果 ...
- mysql添加临时索引_mysql 中添加索引的三种方法
在mysql中有多种索引,有普通索引,全文索引,唯一索引,多列索引,小伙伴们可以通过不同的应用场景来进行索引的新建,在此列出三种新建索引的方法 mysql 中添加索引的三种方法 1.1 新建表中添加索 ...
- mysql如何删除数据_MySQL中删除数据的两种方法
1. 在MySQL中有两种方法可以删除数据: 一种是delete语句,另一种是truncate table语句. delete语句可以通过where对要删除的记录进行选择,而使用truncate ta ...
- 重置mysql+密码_MySQL重置root密码的几种方法(windows+Linux)
重置root密码的方法: windows系统下: 1.停止mysql服务: 2.新建文件init-root.txt,写上如下内容: update mysql.user set password = p ...
最新文章
- SQL代码-创建DeskInfo表
- jetspeed 安装及数据库配置
- 信息安全系统设计基础第一周学习总结
- 软件需求说明的前世和今生
- jQuery 判断鼠标键
- 细粒度权限控制 linux,FGAC(细粒度访问控制)/VPD
- cygwin安装skyeye 所需的软件包列表
- linux一键搭建ddns,LINUX下搭建DDNS
- 24c04硬件地址位_硬件刷题篇(一)
- 计算机网络—传输层(思维导图)
- winform list集合怎么 in过滤_你有真正把 Python Set 当作数学集合吗?
- 使用Kotlin的Android TextView –全面教程
- STM32F407 硬件IIC驱动MCP4017 数字电位器
- MINGW里面没有mingw32 make.exe
- 浅析 微信公共平台消息 开发原理
- 看这玩意复习你还会挂科?《web开发1篇》
- Markdown学习
- Python爬虫入门4:使用IE浏览器获取网站访问的http信息
- linux 用7zip解压rar,Linux7-rar文件的压缩及解压方法
- 股票的大底部形态,常见几种底部形态详解