当我尝试创建带有组函数条件和普通列条件的case表达式时,我遇到了问题。
表:STG
+ -------+--------+------+----------+ | Ref_ID | Actual | Paid | Reason | + -------+--------+------+----------+ | H1 | 360 | 0 | | | H1 | 360 | 0 | | | H1 | 0 | 0 | | | H1 | 0 | 0 | | | H1 | 0 | 0 | | | H1 | 360 | 0 | | | H1 | 360 | 0 | | | H1 | 360 | 0 | | | H1 | 0 | 0 | | | H1 | 0 | 0 | | | H1 | 360 | 0 | | | H1 | 0 | 0 | | | H1 | 360 | 0 | | | H1 | 360 | 0 | | | H1 | 360 | 0 | | | H1 | 360 | 0 | | | H1 | 360 | 0 | | | H1 | 0 | 0 | | | H1 | 0 | 0 | | | H1 | 0 | 0 | | | H1 | 360 | 0 | | | H1 | 360 | 0 | | | H1 | 0 | 0 | | | H1 | 360 | 0 | | | H1 | 0 | 0 | | | H1 | 360 | 0 | | | H1 | 360 | 0 | | | H1 | 0 | 0 | | | H1 | 360 | 0 | | | H1 | 0 | 0 | | | H1 | 360 | 0 | | | H1 | 0 | 480 | TRAINING | | H1 | 0 | 0 | | | H1 | 360 | 0 | | | H1 | 360 | 0 | | + -------+--------+------+----------+
代码已经如下:
说明:如果每天的实际小时数超过480,则需要将其视为480。 8小时/天* 60 = 480。 然后将实际总和扩展1440,然后需要从实际总和中扣除。
在同一查询中,我必须将所有实际值与已支付的总和(如果原因是培训,则是已支付的小时数)
SELECT
CASE WHEN (SUM(CASE WHEN (ACTUAL)>480 THEN 480 ELSE (ACTUAL) END))>1440 THEN
((SUM(CASE WHEN (ACTUAL)>480 THEN 480 ELSE (ACTUAL) END))-1440) ELSE 0
END SINGLE_RATE
FROM STG WHERE REF_ID='H1'
GROUP BY REF_ID;
我试图进行如下修改:
SELECT
CASE WHEN (SUM(CASE WHEN (ACTUAL)>480 THEN 480 ELSE (ACTUAL) END)+(case when reason = 'training' then paid else 0 end ))>1440 THEN
((SUM(CASE WHEN (ACTUAL)>480 THEN 480 ELSE (ACTUAL) END)+(case when reason = 'training' then paid else 0 end ))-1440) ELSE 0
END SINGLE_RATE
FROM STG WHERE REF_ID='H1'
GROUP BY REF_ID;
但出现以下错误:
ORA-00979: not a GROUP BY expression
00979. 00000 - "not a GROUP BY expression"
*Cause:
*Action:
也尝试过:
SELECT
(sum ( (CASE WHEN (ACTUAL)>480 THEN 480 ELSE (ACTUAL) END) + case when reason = 'training' then paid else 0 end )-1440) SINGLE_RATE
FROM STG WHERE REF_ID='H1'
GROUP BY REF_ID
having sum ( (CASE WHEN (ACTUAL)>480 THEN 480 ELSE (ACTUAL) END) + case when reason = 'training' then paid else 0 end )>1440;
但是paid
的金额未计算。仅添加actual
。
请提出您的建议。
答案 0 :(得分:2)
根据业务规则,您始终希望在actual
计算中包括sum()
,但是仅当原因为paid
时才包括'training'
。该规则很容易在case
语句中表达。此外,您有一个上限,actual
不能超过480。可以使用least()
函数来满足该规则:
select ref_id
, sum ( least(actual, 480) + case when reason = 'training' then paid else 0 end ) as tot
from stg
group by ref_id
/
坦率地说,我仍然不清楚您要使用1440实现的目标。如果您发布了一些示例数据,其中涵盖了您要处理的所有情况,并且您从该示例数据中获得了所需的输出,那么生活将会更加轻松。但是我还是要猜:
with cte as (
select ref_id
, sum ( least(actual, 480) + case when reason = 'training' then paid else 0 end ) as tot
from stg
group by ref_id
)
select ref_id
case
when tot <= 1440 then tot
else tot - 1440
end as adjusted_tot
from cte
/
和以前一样,如果没有提供您想要的答案,请编辑您的问题。您的要求越明确,您越有可能及时得到答案。