[英]Populating an entire column with same value returned from a CASE statement
我正在尝试通过整个s_date
/ part_no
分组从结果CASE语句填充具有相同结果值的列。
我们尝试了多种不同的路线来使递归能够满足我们的需求,但是没有运气。 计算非常棘手,而且我们知道SQL并不是递归的最佳选择,因此我们正试图找到一种替代途径,以暂时满足客户需求和时间紧缩。
SELECT
s_date,
part_no,
i_group,
s_level,
p_category,
qty_filled,
qty_total,
relief_amt,
extreme_amt,
curr_mth_note,
CASE
WHEN curr_mth_note IS NOT NULL
AND i_group = '1'
AND s_level = '80' THEN qty_filled
ELSE NULL
END AS g1s1_filled
FROM
(
SELECT
t1.s_date,
t1.part_no,
t1.i_group,
t1.s_level,
t1.p_category,
t1.qty_filled,
t1.qty_total,
mv.relief_amt,
mv.extreme_amt,
mv.curr_mth_note,
FROM
multi_table mv,
t_table t1
WHERE
t1.part_no = mv.part_no
AND mv.part_no = 'xxxx'
AND t1.s_date = mv.s_date
AND t1.s_date = '201805'
GROUP BY
t1.s_date,
t1.i_group,
t1.s_level,
t1.part_no,
t1.p_category,
t1.qty_filled,
t1.qty_total,
mv.relief_amt,
mv.extreme_amt,
mv.curr_mth_note,
ORDER BY
t1.s_date,
t1.i_group,
t1.s_level DESC
)
ORDER BY
s_date,
part_no,
i_group,
DECODE(s_level, '80', 1, '100', 2, 'Late', 3)
上面的当前输出如下所示:
我试图/希望得到的是整个g1s1_filled
列,以显示对于所有可用日期/部分组合, i_group = '1' and s_level = '80'
的相同67数量。
因此,对于该列显示以下内容:
G1S1_FILLED
67
67
67
67
67
我研究了如何尝试在不出现运气的情况下使用where而不是when。 这样会有很多其他的列,我最终也可以在这些列上进行计算。
您可以在SELECT
子句中使用条件分析最小值。 我没有您的数据,因此我将在SCOTT.EMP
表上使用类似的查询进行说明-假设我想用一位特定员工的薪水来填充NEWCOL
。 我会这样做:
select empno, ename, sal, job, deptno,
min(case when empno = 7499 and ename = 'ALLEN' then sal end) over () as newcol
from scott.emp;
EMPNO ENAME SAL JOB DEPTNO NEWCOL
---------- ---------- ---------- --------- ---------- ----------
7369 SMITH 800 CLERK 20 1600
7499 ALLEN 1600 SALESMAN 30 1600
7521 WARD 1250 SALESMAN 30 1600
7566 JONES 2975 MANAGER 20 1600
7654 MARTIN 1250 SALESMAN 30 1600
7698 BLAKE 2850 MANAGER 30 1600
7782 CLARK 2450 MANAGER 10 1600
7788 SCOTT 3000 ANALYST 20 1600
7839 KING 5000 PRESIDENT 10 1600
7844 TURNER 1500 SALESMAN 30 1600
7876 ADAMS 1100 CLERK 20 1600
7900 JAMES 950 CLERK 30 1600
7902 FORD 3000 ANALYST 20 1600
7934 MILLER 1300 CLERK 10 1600
如果(在您的问题中)如果只有一行包含I_GROUP
和S_LEVEL
的值的“特殊”组合,那么您可以使用(有条件的,分析的) MIN
或MAX
甚至AVG
或SUM
它们都将等于单个值,在您的情况下为67。 如果这样的值不止一个,那么您将需要做出选择:您想要MIN
, MAX
, AVG
还是其他东西。 无论如何,您仍然可以使用相同的想法。
我想你想要一个窗口函数:
SUM(CASE WHEN curr_mth_note IS NOT NULL AND i_group = '1' AND
s_level = '80'
THEN qty_filled
END) OVER (PARTITION BY s_date, part_no) AS g1s1_filled
代替case语句,为其编写一个子查询
(select qty_filled
from t_Table
where
i_group = '1' and
s_level = '80' and
rownum = 1
) as g1s1_filled
您可以删除CASE
表达式,然后将整个查询( ORDER BY
子句除外)移至CTE。 然后,您可以自JOIN
它,将相关的g1s1_filled
附加到每一行。
注意:定义自联接条件时必须小心; 我在下面提供了一个建议,您可能需要对其进行完善。
查询:
WITH cte AS (
SELECT
s_date,
part_no,
i_group,
s_level,
p_category,
qty_filled,
qty_total,
relief_amt,
extreme_amt,
curr_mth_note
FROM
(
SELECT
t1.s_date,
t1.part_no,
t1.i_group,
t1.s_level,
t1.p_category,
t1.qty_filled,
t1.qty_total,
mv.relief_amt,
mv.extreme_amt,
mv.curr_mth_note,
FROM
multi_table mv,
t_table t1
WHERE
t1.part_no = mv.part_no
AND mv.part_no = 'xxxx'
AND t1.s_date = mv.s_date
AND t1.s_date = '201805'
GROUP BY
t1.s_date,
t1.i_group,
t1.s_level,
t1.part_no,
t1.p_category,
t1.qty_filled,
t1.qty_total,
mv.relief_amt,
mv.extreme_amt,
mv.curr_mth_note,
ORDER BY
t1.s_date,
t1.i_group,
t1.s_level DESC
)
)
SELECT a.*, b.qty_filled as g1s1_filled
FROM
cte AS a
INNER JOIN cte as b
ON b.s_date = a.s_date
AND b.part_no = a.part_no
AND b.i_group = '1'
AND b.s_level = '80'
AND b.curr_mth_note IS NOT NULL
ORDER BY
a.s_date,
a.part_no,
a.i_group,
DECODE(a.s_level, '80', 1, '100', 2, 'Late', 3)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.