提问人:DBanks 提问时间:10/30/2023 最后编辑:DaiDBanks 更新时间:10/30/2023 访问量:51
简化我的存储过程(cte、merge)
Simplifying my stored procedure (cte, merge)
问:
我拼凑了一个相当长的、可能效率低下的存储过程。sproc 接收 SKU 的 JSON 以及一些参数,以便使用同一组数据批量更新两个不同的表。数据本身来自第一个表 (ProductValidation),因此这些数据将始终为 UPDATE,但第二个表可能包含也可能没有这些记录。(我只是将这两种情况都保留为合并 UPDATE 或 INSERT,即使第一种情况始终是 UPDATE - 但我认为这不会对性能造成太大影响......
如果您看到我可以做得更好的地方,请告诉我?我有点新手,所以期待你们的专业人士,谢谢!
WITH cte AS (
SELECT
SellingSkuCode AS SellingSkuCodez
FROM
OPENJSON( @json ) WITH (
SellingSkuCode varchar(100),
MaterialDescription varchar(8000),
TranslatedMaterialDescription varchar(8000),
LocalErpSubbrand varchar(8000),
HarmonizedSubbrand varchar(500),
GrossRevenue varchar(100),
Priority varchar(100),
Validated varchar(100),
MarketUnitName varchar(100),
UpdatedBy varchar(100)
)
),
cte2 AS (
SELECT
*
FROM
cte
INNER JOIN ProductValidation B ON cte.SellingSkuCodez = B.SellingSkuCode
)
MERGE ProductValidation original
USING cte2 modified ON (
original.SellingSkuCode = modified.SellingSkuCode
AND
original.MarketUnitName = @Market
)
WHEN MATCHED THEN UPDATE SET
original.SellingSkuCode = modified.SellingSkuCode,
original.MaterialDescription = modified.MaterialDescription,
original.TranslatedMaterialDescription = modified.TranslatedMaterialDescription,
original.LocalErpSubbrand = modified.LocalErpSubbrand,
original.HarmonizedSubbrand = @HarmonizedSubbrand,
original.GrossRevenue = modified.GrossRevenue,
original.Priority = modified.Priority,
original.Validated = modified.Validated,
original.MarketUnitName = @Market,
original.UpdatedBy = @UpdatedBy
WHEN NOT MATCHED BY TARGET THEN
INSERT (
SellingSkuCode,
MaterialDescription,
TranslatedMaterialDescription,
LocalErpSubbrand,
HarmonizedSubbrand,
GrossRevenue,
Priority,
Validated,
MarketUnitName,
UpdatedBy
)
VALUES (
SellingSkuCode,
modified.MaterialDescription,
modified.TranslatedMaterialDescription,
modified.LocalErpSubbrand,
@HarmonizedSubbrand,
modified.GrossRevenue,
modified.Priority,
modified.Validated,
@Market,
@UpdatedBy
);
WITH cte AS (
SELECT
SellingSkuCode AS SellingSkuCodez
FROM
OPENJSON(@json) WITH (
SellingSkuCode varchar(100),
MaterialDescription varchar(8000),
TranslatedMaterialDescription varchar(8000),
LocalErpSubbrand varchar(8000),
HarmonizedSubbrand varchar(500),
GrossRevenue varchar(100),
Priority varchar(100),
Validated varchar(100),
MarketUnitName varchar(100),
UpdatedBy varchar(100)
)
),
cte2 AS (
SELECT
*
FROM
cte
INNER JOIN ProductValidation B ON cte.SellingSkuCodez = B.SellingSkuCode
)
MERGE ProductValidation_Feedback original
USING cte2 modified ON (
original.SellingSkuCode = modified.SellingSkuCode
AND
original.MarketUnitName = modified.MarketUnitName
)
WHEN MATCHED THEN UPDATE SET
original.SellingSkuCode = modified.SellingSkuCode,
original.MaterialDescription = modified.MaterialDescription,
original.TranslatedMaterialDescription = modified.TranslatedMaterialDescription,
original.LocalErpSubbrand = modified.LocalErpSubbrand,
original.HarmonizedSubbrand = @HarmonizedSubbrand,
original.GrossRevenue = modified.GrossRevenue,
original.Priority = modified.Priority,
original.Validated = modified.Validated,
original.MarketUnitName = @Market,
original.UpdatedBy = @UpdatedBy
WHEN NOT MATCHED BY TARGET THEN
INSERT (
SellingSkuCode,
MaterialDescription,
TranslatedMaterialDescription,
LocalErpSubbrand,
HarmonizedSubbrand,
GrossRevenue,
Priority,
Validated,
MarketUnitName,
UpdatedBy
)
VALUES (
SellingSkuCode,
modified.MaterialDescription,
modified.TranslatedMaterialDescription,
modified.LocalErpSubbrand,
@HarmonizedSubbrand,
modified.GrossRevenue,
modified.Priority,
modified.Validated,
@Market,
@UpdatedBy
);
我花了很长时间才让它发挥作用,因为我被困在加入 CTE 上。现在它可以工作了,但试图看看是否可以从速度/性能角度改进它。
答: 暂无答案
上一个:通过对象隔离实现原子性
评论
HOLDLOCK
MERGE
varchar
varchar
nvarchar
WHEN MATCHED
SELECT src.... EXCEPT SELECT tgt...
MERGE
tgt
TARGET
src
SOURCE