使用不同的条件选择同一列两次

6qqygrtg  于 2021-06-25  发布在  Mysql
关注(0)|答案(2)|浏览(301)

我很难达到sql的目标。花了几个小时在这里和其他地方阅读类似的问题,但我的问题似乎是独一无二的。
我的数据库有几列:
客户名称| |项目| |类型| |日期| |成本| |更正
  客户1        项目1 电视   2018-1  100       不
  客户1        项目1 电视   2018-1  -50       对
所以这张表需要一些解释(它的每一行都有一个auto_inc id。)correction=no表示这是一个原始值,在预测财务时创建“是”意味着这是价格的后期调整。
我的目标是把预测和实际并排看。所以每个月,它都应该加上correction=no值(这对于

SELECT date, SUM(cost) FROM table WHERE correction='no' GROUP BY date)

然后列出所有实际值(不带where子句的sum)。
行需要根据客户机、项目、类型和日期进行匹配。这看起来很简单,但我已经得到单行错误,自然。从逻辑上讲,我找不到一个解决方案来解决这个问题,而且我更像是一个初学者。
所以我想:
包含月份的列,
包含sum(cost)的列,其中correction='no',
还有一个列,列出了所有成本的总和,当然这些成本都是按月份划分的。
我希望你能提供一些意见。

nvbavucw

nvbavucw1#

使用条件聚合。
聚合函数对一组值执行计算并返回单个值。
条件聚合是对条件表达式的聚合,例如 correction = 'no' . 这是通过一个 CASE 在聚合函数中构造( SUM 此处):

select 
  year(date), month(date),
  sum(case when correction = 'no' then cost end) as sum_no,
  sum(case when correction = 'yes' then cost end) as sum_yes,
  sum(cost) as sum_total
from mytable
group by year(date), month(date)
order by year(date), month(date;
klsxnrf1

klsxnrf12#

在这种情况下,我喜欢使用公共表表达式(cte)来分解它。这允许我计算每个客户/项目/月的预计成本,并将其放在一个cte中,然后分别计算另一个cte中的实际成本,然后从每个结果中查询。

WITH projection AS (
    SELECT [client name], project, type, date, SUM(cost) cost FROM test WHERE correction='no' GROUP BY [client name], project, type, date
),
actual AS (
    SELECT [client name], project, type, date, SUM(cost) cost FROM test GROUP BY [client name], project, type, date
)
SELECT p."client name", p.project, p.type, p.date, p.cost AS "projected cost", a.cost AS "actual cost"
FROM projection p
JOIN actual a ON a."client name" = p."client name"
AND a.project = p.project 
AND a.type = p.type
AND a.date = p.date

注意:我使用以下方法构建测试表和值:

CREATE TABLE test ([client name] VARCHAR(100), project VARCHAR(100), type VARCHAR (100), date VARCHAR(100), cost INT, correction VARCHAR(100))

INSERT INTO test VALUES ('Client1', 'Project1', 'TV','2018-1', 100, 'no')
INSERT INTO test VALUES ('Client1', 'Project1', 'TV','2018-1', 200, 'no')
INSERT INTO test VALUES ('Client1', 'Project1', 'TV','2018-2', 300, 'no')
INSERT INTO test VALUES ('Client1', 'Project1', 'TV','2018-2', 400, 'no')

INSERT INTO test VALUES ('Client1', 'Project1', 'TV','2018-1', -50, 'yes')
INSERT INTO test VALUES ('Client1', 'Project1', 'TV','2018-2', -99, 'yes')
INSERT INTO test VALUES ('Client1', 'Project1', 'TV','2018-2', -75, 'yes')

INSERT INTO test VALUES ('Client1', 'Project2', 'TV','2018-1', 10, 'no')
INSERT INTO test VALUES ('Client1', 'Project2', 'TV','2018-1', 20, 'no')
INSERT INTO test VALUES ('Client1', 'Project2', 'TV','2018-2', 30, 'no')
INSERT INTO test VALUES ('Client1', 'Project2', 'TV','2018-2', 40, 'no')

INSERT INTO test VALUES ('Client1', 'Project2', 'TV','2018-1', -50, 'yes')
INSERT INTO test VALUES ('Client1', 'Project2', 'TV','2018-2', -99, 'yes')

我的结果是:

"client name"   project   type   date     "projected cost"  "actual cost"
--------------- --------- ------ -------- ---------------- --------------
Client1         Project1  TV     2018-1                300            250
Client1         Project1  TV     2018-2                700            526
Client1         Project2  TV     2018-1                 30            -20
Client1         Project2  TV     2018-2                 70            -29

相关问题