MySQL筛选特定值但保留非匹配行的查询问题
MySQL记账凭证筛选查询问题解决
场景与原始数据
现有journal_entry表(共517行数据),执行以下查询获取jev_no为'2022-03-001'的原始数据:
SELECT jev_no, account_code, debit, credit FROM journal_entry WHERE jev_no = '2022-03-001'
返回结果:
| jev_no | account_code | debit | credit |
|---|---|---|---|
| 2022-03-001 | 50501010 | 800.00 | 0.00 |
| 2022-03-001 | 20201010 | 0.00 | 800.00 |
| 2022-03-001 | 10102010 | 0.00 | 521.00 |
| 2022-03-001 | 20201070 | 521.00 | 0.00 |
筛选规则
需按以下规则筛选数据,同时保留不匹配规则的行:
- 包含
account_code = 10102010且credit > 0的行 - 排除
account_code = 20201010的行 - 包含
account_code = 20201070且credit > 0的行 - 排除
account_code = 50299990且credit > 0的行 - 排除
account_code = 50213040且credit > 0的行 - 排除
account_code = 10305010且credit > 0的行
原查询问题
原查询使用AND连接所有条件,导致逻辑矛盾(例如要求同一行同时满足account_code = 10102010和account_code = 20201070),因此无返回结果:
SELECT j.jev_no, j.account_code, j.debit, j.credit FROM journal_entry j WHERE (account_code = 10102010 and j.credit > 0) AND account_code <> 20201010 AND (account_code = 20201070 and j.credit > 0) AND ( account_code <> 50299990 and j.credit > 0) AND (account_code <> 50213040 and j.credit > 0) AND (account_code <> 10305010 and j.credit > 0) AND jev_no = '2022-03-001'
正确查询语句
正确逻辑应为:先限定jev_no,再排除所有不符合要求的行,同时保留符合包含规则及无匹配规则的行:
SELECT jev_no, account_code, debit, credit FROM journal_entry WHERE jev_no = '2022-03-001' AND NOT ( -- 排除规则2:直接排除该account的所有行 account_code = '20201010' -- 排除规则4:特定account且credit>0 OR (account_code = '50299990' AND credit > 0) -- 排除规则5:特定account且credit>0 OR (account_code = '50213040' AND credit > 0) -- 排除规则6:特定account且credit>0 OR (account_code = '10305010' AND credit > 0) -- 规则3的反向:排除该account中credit不大于0的行 OR (account_code = '20201070' AND credit <= 0) )
预期结果
执行上述查询后,将得到预期结果:
| jev_no | account_code | debit | credit |
|---|---|---|---|
| 2022-03-001 | 50501010 | 800.00 | 0.00 |
| 2022-03-001 | 10102010 | 0.00 | 521.00 |
内容的提问来源于stack exchange,提问作者Anonymous Coder
相关产品推荐
相关产品推荐

