简体   繁体   English

mysql查询总和的差异

[英]Difference on sum totals on mysql query

I am having different results on what appears to be the same query. 我对似乎相同的查询有不同的结果。 I am very confused on why the total differs from the queries. 我对为什么总数与查询不同感到非常困惑。 Hopefully someone has an explanation on this issue and maybe say which should be the correct total. 希望有人对此问题有一个解释,也许说应该是正确的总数。 Thank you 谢谢

select sum(tm_hours) 
FROM bhds_timecard 
WHERE (tm_notes = 'Session' 
 OR tm_notes = 'Intake' 
 OR tm_notes = 'OT' 
 or tm_notes = 'PT' 
 or tm_notes = 'Speech') 
AND (tm_date BETWEEN '2016-04-01' AND '2016-04-30')

This totals 1792.25 总计1792.25

SELECT SUM(tm_hours) 
FROM bhds_timecard 
WHERE (tm_date BETWEEN '2016-04-01' AND '2016-04-30') 
AND tm_notes = 'Session' 
OR tm_notes = 'Intake' 
OR tm_notes = 'OT' 
OR tm_notes = 'PT' 
OR tm_notes = 'Speech'

This totals 1796.25 总计1796.25

If you understand why 5 + 3 * 2 = 11 then this will help understand the source of your problem. 如果您了解为什么5 + 3 * 2 = 11,那么这将有助于您了解问题的根源。 Some people may mistakenly think the above calculation should give you 16 because they are unaware of the order of operations. 某些人可能会错误地认为上述计算应该给您16,因为他们不知道操作顺序。 Multiplication takes precedence over addition so it is done first. 乘法优先于加法,因此首先完成乘法。

Likewise, AND has a higher precedence than OR so it is done first. 同样,AND的优先级高于OR,因此优先执行。 Check out the Operator Precedence section in the MySQL reference manual. 查看MySQL参考手册中的“ 运算符优先级”部分。

This is likely the code you were trying to build: 这可能是您尝试构建的代码:

SELECT SUM(tm_hours) 
FROM bhds_timecard 
WHERE tm_date BETWEEN '2016-04-01' AND '2016-04-30'
AND (tm_notes = 'Session' 
OR tm_notes = 'Intake' 
OR tm_notes = 'OT' 
OR tm_notes = 'PT' 
OR tm_notes = 'Speech');

In this case, since parentheses override the standard order of operations, everything in the parentheses gets executed first (which are all the OR statements). 在这种情况下,由于括号会覆盖操作的标准顺序,因此括号中的所有内容都会首先执行(都是OR语句)。 Therefore the entire parenthetical section will evaluate to TRUE if only one of the conditions evaluates to TRUE). 因此,如果只有一个条件为TRUE,则整个括号部分将为TRUE。 Next all of your ANDS get evaluated and you have your answer. 接下来,您的所有ANDS都将得到评估,您将得到答案。

Second query must be like that: 第二个查询必须是这样的:

SELECT SUM(tm_hours) FROM bhds_timecard WHERE (tm_date BETWEEN '2016-04-01' AND '2016-04-30') 
AND (tm_notes = 'Session' OR tm_notes = 'Intake' OR tm_notes = 'OT' OR tm_notes = 'PT' OR tm_notes = 'Speech')

You lose the ( bracket for second group of conditions 您输了(第二组条件的方括号

The first query is evaluating all of your OR s as one condition - 第一个查询将所有OR视为一个条件-

WHERE (tm_notes = 'Session' 
 OR tm_notes = 'Intake' 
 OR tm_notes = 'OT' 
 or tm_notes = 'PT' 
 or tm_notes = 'Speech')
AND (tm_date BETWEEN '2016-04-01' AND '2016-04-30')

If a row meets any of those conditions, it evaluates as true and then moves on to the date constraint. 如果某行满足任何这些条件,则其结果为true,然后继续执行日期约束。 So there's really only 2 top-level condition in the first query. 因此,第一个查询中实际上只有2个顶级条件。

The second query actually has 6 conditions - 第二个查询实际上有6个条件-

WHERE (tm_date BETWEEN '2016-04-01' AND '2016-04-30') 
AND tm_notes = 'Session' 
OR tm_notes = 'Intake' 
OR tm_notes = 'OT' 
OR tm_notes = 'PT' 
OR tm_notes = 'Speech'

If any of the 6 OR s are true, the whole WHERE clause is evaluated as true. 如果6个OR的任何一个为true,则将整个WHERE子句评估为true。

Your first query conditions are like this 您的第一个查询条件是这样的

Where
--first condition 
(tm_notes = 'Session' OR tm_notes = 'Intake' OR tm_notes = 'OT' or tm_notes = 'PT' or tm_notes = 'Speech')
AND 
-- second condition
(tm_date BETWEEN '2016-04-01' AND '2016-04-30')

you choose both the conditions to be true, first condition itself a combination of conditions, 您选择两个条件都为真,首先将条件本身组合为条件,

While in the second query you have this many conditions with OR and so if any of the conditions gets true the whole condition pattern gets true and so there is the difference in the result 在第二个查询中,您具有使用OR许多条件,因此,如果任何条件为真,则整个条件模式都为真,因此结果存在差异

Where
-- first condition
(tm_date BETWEEN '2016-04-01' AND '2016-04-30') 
AND 
-- second condition
tm_notes = 'Session' 
OR
-- third condition 
tm_notes = 'Intake' 
OR 
-- fourth condition
tm_notes = 'OT' 
OR 
-- fifth condition
tm_notes = 'PT' 
-- sixth condition
OR 
tm_notes = 'Speech'

AND & OR work like + & - ANDOR工作方式类似于+-

a+(b*c) is not the same as (a+b)*c a+(b*c)(a+b)*c

Same for AND & OR ANDOR相同

a OR (b AND c) is not the same as (a OR b) AND c a OR (b AND c)(a OR b) AND c

So be carefull with brackets when you mix up AND & OR 因此,当您将ANDOR混合使用时AND OR

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM