首先,这不是在问SQL,count(列)和count(*)之间有什么区别?.
假设我有一个users带有主键的表user_id和另一个logged_in描述用户是否立即登录的字段.
跑步之间有区别吗?
SELECT COUNT(user_id) FROM users WHERE logged_in=1
和
SELECT COUNT(logged_in) FROM users WHERE logged_in=1
查看有多少用户被标记为已登录?也许与索引不同?
如果有特定于DB的细微差别,我正在运行MySQL.
Eso*_*ame 12
在MySQL中,count函数不会计算空表达式,因此两个查询的结果可能不同.正如评论和Remus的回答中所提到的,这是SQL的一般规则和规范的一部分.
例如,请考虑以下数据:
user_id logged_in
1 1
null 1
Run Code Online (Sandbox Code Playgroud)
SELECT COUNT(user_id)在这个表上将返回1,但SELECT COUNT(logged_in)将返回2.
实际上,问题中的示例结果应该始终相同,只要表格构造正确,但使用的索引和查询计划可能会有所不同,即使结果是相同的.此外,如果这是一个简化的示例,计算不同的列也可能会更改结果.
另请参阅此问题:MySQL COUNT()和null
对于记录:两个查询返回不同的结果.正如规范所说:
返回SELECT语句检索的行中expr 的非NULL值的计数.
您可能会争辩说,无论如何都会过滤掉logged_in=1NULL logged_in行的条件,并且user_id表中不会有NULL users.虽然这可能是真的,但它并没有改变查询不同的基本原理.您要求查询优化器在上面进行所有逻辑推理,对于您来说它们可能是显而易见的,但对于优化器可能不是.
现在,假设结果实际上在两者之间始终相同,答案很简单:不要在生产中运行这样的查询(我的意思是其中之一).无论你如何切片,都是扫描.logged_in事实上基数太低了.保留一个计数器,在每次登录和每次注销事件时更新它.它会随时间漂移,根据需要经常刷新(每天一次,每小时一次).
至于问题本身:SELECT COUNT(somefield) FROM sometable可以使用较窄的索引somefield导致较少的IO.建议使用,*因为这个空间可供优化器使用它认为合适的任何索引(这会因产品而异,具体取决于我们处理的查询优化器的智能程度,YMMV).但是当你开始添加WHERE子句时,可能的替代方法(=要使用的索引)很快就会消失.
| 归档时间: |
|
| 查看次数: |
197 次 |
| 最近记录: |