sql - 在这种情况下,是否可以基于集合而不是游标循环?
问题描述
当前代码:
DECLARE thisLoop CURSOR FOR
SELECT IdOld, IdNew
FROM @fieldNewOld;
OPEN thisLoop;
FETCH NEXT FROM thisLoop INTO @fIdOld, @fIdNew;
WHILE @@FETCH_STATUS = 0
BEGIN
UPDATE dbo.mel
SET melCode = REPLACE(melCode, '_' + CONVERT(varchar(50),@fIdOld), '_' + CONVERT(varchar(50),@fIdNew))
where fID = (select IdNew from @newForm) and melCode LIKE ('%_' + CONVERT(varchar(50), @fIdOld) + '%')
FETCH NEXT FROM thisLoop INTO @fIdOld, @fIdNew
END;
CLOSE thisLoop;
DEALLOCATE thisLoop;
围绕这个还有更多的事情发生,但基本上我正在制作数据集的副本。@fieldNewOld 包含旧 ID 和新 ID。dbo.mel 中的 melCode 包含(以专有语言编写)可以引用所有旧 ID 的代码。它将被引用为“myVar_1234”之类的东西,其中 1234 将是旧 ID 之一。复制时,我想用 melCode 中的新 id 替换所有旧 id。
我可以使用上面显示的游标循环来做到这一点,但是当数据集很大时它会非常慢。我也试过下面的代码,但是如果melCode中有多个旧的id,它会尝试多次更新同一行并抛出错误:
MERGE INTO dbo.mel b
USING @fieldNewOld a
ON b.fID = (select IdNew from @newForm) and b.melCode LIKE ('%_' + CONVERT(varchar(50), a.IdOld) + '%')
WHEN MATCHED THEN
UPDATE
SET b.melCode = REPLACE(b.melCode, '_' + CONVERT(varchar(50),a.IdOld), '_' + CONVERT(varchar(50),a.IdNew));
有什么方法可以以基于集合的方式完成此操作,还是我被光标循环的缓慢所困扰?
示例数据:
@fieldNewOld
IdOld | IdNew
1234 | 5678
1235 | 5679
1236 | 5680
melCode(所有这些都在一行中)
userok("My variable: " + myVar_1234)
myVar_1234 = "this is a test"
newVar_1236 = "here is some more data"
复制后,我希望 melCode 看起来像这样:
userok("My variable: " + myVar_5678)
myVar_5678 = "this is a test"
newVar_5680 = "here is some more data"
解决方案
您可以在 UPDATE 中使用 JOIN。
UPDATE m
SET melCode = REPLACE(melCode, '_' + CONVERT(varchar(50),IdOld), '_' + CONVERT(varchar(50),fIdNew))
FROM dbo.mel m
JOIN @fieldNewOld fno ON m.melCode LIKE ('%_' + CONVERT(varchar(50), IdOld) + '%')
where fID = (select IdNew from @newForm) ;
这似乎您在 melCode 中有一个复合值。我的建议是将值拆分为 2 列或更多列,并将 melCode 作为计算列。
推荐阅读
- sql - 使用超过 60 亿次操作加速 SQL 查询
- android - 使用 ConstraintLayout 将水平回收视图放置在特定位置
- jmeter - 使用 Jmeter 处理 SSE 请求
- c# - 如何调用通用输入类型类的方法
- java - Itext5 文档未正确关闭
- reactjs - 如何在这里传递状态?
- asp.net-web-api - 从 NSwag 招摇中过滤模式
- elasticsearch - 如何在 Elastic Search 中通过术语聚合获取额外数据?
- postgresql - 检查 postgresql 函数中的行数
- javascript - Mapbox 上超出了最大调用堆栈大小