SQL - 如果对应的值都相同,则使用值更新字段
Posted
技术标签:
【中文标题】SQL - 如果对应的值都相同,则使用值更新字段【英文标题】:SQL - update field with a value, if corresponding values are all the same 【发布时间】:2021-06-16 18:44:31 【问题描述】:我手头有一个有趣的任务,我正试图弄清楚如何去做。
假设我的表格中有以下数据:
Num1 Acct Amt Type1 Type2 AmtX AmtY AcctBadInd
X12 111 90 X 1 NULL NULL NULL
X12 222 -90 X 1 NULL NULL NULL
X12 333 90 X 1 NULL NULL NULL
Y33 111 75 Y 1 NULL NULL NULL
Y33 444 -75 Y 1 NULL NULL NULL
Z44 111 55 Y 1 NULL NULL NULL
Z44 111 55 Y 0 NULL NULL NULL
Z44 444 -65 Y 1 NULL NULL NULL
以下是几个示例。唯一需要注意的是,给定的 Num1 可以有任意数量的记录,但始终 >= 2。因此它可能是 2、3、4、5,并且相同的逻辑适用于所有情况。
验证所有Type2=1
记录的ABS(AMT)
是否相同。如果所有 3 条记录都具有相同的 AMT,则该 Num1 为 SET AMTX=ABS(AMT)
。或者,如果Type1 was Y for X12
- 那么我们将改为更新AmtY = ABS(AMT)
Num1 = Y33
- 在这种情况下,我们再次要验证ABS(AMT)
与Type2=1
相同。如果它们相等,那么因为Type1=Y
,我们将设置AmtY =75
Num1=Z44
- 在这种情况下,再次验证Type2=1
的 ABS(AMT) 是否相同。如果不相等,则不要更新AmtY,而是设置AcctBadInd = 1
最终结果
Num1 Acct Amt Type1 Type2 AmtX AmtY AcctBadInd
X12 111 90 X 1 90 NULL NULL
X12 222 -90 X 1 90 NULL NULL
X12 333 90 X 1 90 NULL NULL
Y33 111 75 Y 1 NULL 75 NULL
Y33 444 -75 Y 1 NULL 75 NULL
Z44 111 55 Y 1 NULL NULL 1
Z44 444 -65 Y 1 NULL NULL 1
Z44 111 55 Y 0 NULL NULL NULL
我正在为此苦苦挣扎,我不希望得到答案,但至少希望得到提示或任何帮助,以便我可以继续前进。更重要的是,如果这可以以我想象的方式实现,而无需编写上帝知道有多少代码。
【问题讨论】:
【参考方案1】:如果我理解正确,您可以这样做:
with cte as (
select * , type2, max(abs(Amt)) minAmt, min(abs(Amt)) maxAmt, count(*) cnt
from table
group by Num1 , type2
);
update t1
set AmtX = case when cnt> 1 and Type2=1 and t1.type1 = 'X' and minAmt = maxAmt then minAmt end
, AmtY = case when cnt> 1 and Type2=1 and t1.type1 = 'Y' and minAmt = maxAmt then minAmt end
, AcctBadInd = case when cnt> 1 and Type2=1 and minAmt <> maxAmt then 1 end
from table t1
join cte on t1.Num1 = cte.Num1
and t1.type2 = cte.type2
【讨论】:
谢谢 - 好主意。我正在考虑取 SUM(ABS(AMT)) 然后除以 Count【参考方案2】:使用窗口函数
with t as (
select *,
AmtXnew = case when min(ABS(AMT)) over(partition by Num1, Type2) = max(ABS(AMT)) over(partition by Num1, Type2)
and Type2 = 1 and Type1 ='X' then ABS(AMT)
else NULL end,
AmtYnew = case when min(ABS(AMT)) over(partition by Num1, Type2) = max(ABS(AMT)) over(partition by Num1, Type2)
and Type2 = 1 and Type1 ='Y' then ABS(AMT)
else NULL end,
AcctBadIndnew = case when min(ABS(AMT)) over(partition by Num1, Type2) <> max(ABS(AMT)) over(partition by Num1, Type2)
and Type2 = 1 then 1 else NULL end
from tbl
)
update t set AmtX = AmtXnew,AmtY = AmtYnew, AcctBadInd = AcctBadIndnew;
【讨论】:
以上是关于SQL - 如果对应的值都相同,则使用值更新字段的主要内容,如果未能解决你的问题,请参考以下文章
Mysql如果某个字段值存在则更新另一个字段的值为原值+100,命令应该如何写?