如何删除目标与源不匹配的特定日期的合并语句中的行
How to delete rows in merge statement for specific date where target doesnt match source
我有一个每天运行的合并语句,因为每天都有新数据转储到我的 table 中,这是我的代码示例:
MERGE SQL_Backup as Target
USING Temp as Source
ON target.code = source.code
WHEN MATCHED THEN update SET
target.saledate = source.saledate,
target.branchcode = source.branchcode
WHEN NOT MATCHED BY TARGET
THEN insert (
code, saledate
)
values (
source.code, source.saledate
)
when not matched by source
then delete;
然而,这会删除我的整个 table,我只想删除今天添加的行,不应触及任何以前的行。
这是源和目标 table 的图像:
Source/Target Table
我有一个标记为 'saledate' 的列,其中包含转储数据的日期,我有一个标记为 'code' 的唯一列,我将其用于合并以检测重复项。
想知道是否有一个 when 与 saledate = today 的来源不匹配然后删除或其他什么?
MERGE 语句只允许在 "WHEN NOT MATCHED BY SOURCE" 子句中使用目标的列和比较项范围内的列。
例如,如果您想按目标 table 中的日期进行过滤,则 MERGE 适合您的情况,但如果您想按源 table 中的日期进行过滤,则这不适用适合 MERGE
这是一个使用简单 table
的完整示例
DROP TABLE IF EXISTS S
DROP TABLE IF EXISTS T
GO
CREATE TABLE S(
id int,
DT DATE
)
DROP TABLE IF EXISTS T
GO
CREATE TABLE T(
id int,
DT DATE
)
INSERT T(id, DT) values (1,'2000-01-01'),(2,'2000-01-01'),(3,'2019-01-01')
INSERT S(id, DT) values (3,'2000-01-01'),(4,'2000-01-01'),(5,'2019-01-01')
GO
SELECT * FROM T
SELECT * FROM S
GO
-- the following query will raise an error
MERGE T as Target USING S as Source
ON Target.id = Source.id
WHEN MATCHED THEN
UPDATE SET Target.id = Source.id + 1000
WHEN NOT MATCHED BY TARGET THEN
insert (id, DT) values (Source.id, Source.DT)
-- Only target columns and columns in the clause scope are allowed in the 'WHEN NOT MATCHED BY SOURCE' clause of a MERGE statement.
-- Using the bellow wil raise an error:
WHEN NOT MATCHED BY SOURCE AND Source.DT > '2005-01-01' THEN DELETE;
GO
-- the following query will work well
MERGE T as Target USING S as Source
ON Target.id = Source.id
WHEN MATCHED THEN
UPDATE SET Target.id = Source.id + 1000
WHEN NOT MATCHED BY TARGET THEN
insert (id, DT) values (Source.id, Source.DT)
-- The bellow will work OK, since I use condition on the TARGET
WHEN NOT MATCHED BY SOURCE AND TARGET.DT > '2005-01-01' THEN DELETE;
GO
SELECT * FROM T
SELECT * FROM S
GO
您可以在WHEN NOT MATCHED BY SOURCE
之后设置AND <clause_search_condition>
。
指定有效的搜索条件,然后指定删除与target_table中的行匹配的行。
例如,删除 source.saledate=今天的行。
MERGE SQL_Backup as Target
USING Temp as Source
ON target.code = source.code
WHEN MATCHED THEN update SET
target.saledate = source.saledate,
target.branchcode = source.branchcode
WHEN NOT MATCHED BY TARGET
THEN insert (
code, saledate
)
values (
source.code, source.saledate
)
WHEN NOT MATCHED BY SOURCE AND source.saledate = CONVERT(varchar(100), GETDATE(), 3)
THEN DELETE;
您的销售日期格式是"dd/mm/yy",所以我们需要转换默认的日期格式。
希望对您有所帮助。
我有一个每天运行的合并语句,因为每天都有新数据转储到我的 table 中,这是我的代码示例:
MERGE SQL_Backup as Target
USING Temp as Source
ON target.code = source.code
WHEN MATCHED THEN update SET
target.saledate = source.saledate,
target.branchcode = source.branchcode
WHEN NOT MATCHED BY TARGET
THEN insert (
code, saledate
)
values (
source.code, source.saledate
)
when not matched by source
then delete;
然而,这会删除我的整个 table,我只想删除今天添加的行,不应触及任何以前的行。
这是源和目标 table 的图像:
Source/Target Table
我有一个标记为 'saledate' 的列,其中包含转储数据的日期,我有一个标记为 'code' 的唯一列,我将其用于合并以检测重复项。
想知道是否有一个 when 与 saledate = today 的来源不匹配然后删除或其他什么?
MERGE 语句只允许在 "WHEN NOT MATCHED BY SOURCE" 子句中使用目标的列和比较项范围内的列。
例如,如果您想按目标 table 中的日期进行过滤,则 MERGE 适合您的情况,但如果您想按源 table 中的日期进行过滤,则这不适用适合 MERGE
这是一个使用简单 table
的完整示例DROP TABLE IF EXISTS S
DROP TABLE IF EXISTS T
GO
CREATE TABLE S(
id int,
DT DATE
)
DROP TABLE IF EXISTS T
GO
CREATE TABLE T(
id int,
DT DATE
)
INSERT T(id, DT) values (1,'2000-01-01'),(2,'2000-01-01'),(3,'2019-01-01')
INSERT S(id, DT) values (3,'2000-01-01'),(4,'2000-01-01'),(5,'2019-01-01')
GO
SELECT * FROM T
SELECT * FROM S
GO
-- the following query will raise an error
MERGE T as Target USING S as Source
ON Target.id = Source.id
WHEN MATCHED THEN
UPDATE SET Target.id = Source.id + 1000
WHEN NOT MATCHED BY TARGET THEN
insert (id, DT) values (Source.id, Source.DT)
-- Only target columns and columns in the clause scope are allowed in the 'WHEN NOT MATCHED BY SOURCE' clause of a MERGE statement.
-- Using the bellow wil raise an error:
WHEN NOT MATCHED BY SOURCE AND Source.DT > '2005-01-01' THEN DELETE;
GO
-- the following query will work well
MERGE T as Target USING S as Source
ON Target.id = Source.id
WHEN MATCHED THEN
UPDATE SET Target.id = Source.id + 1000
WHEN NOT MATCHED BY TARGET THEN
insert (id, DT) values (Source.id, Source.DT)
-- The bellow will work OK, since I use condition on the TARGET
WHEN NOT MATCHED BY SOURCE AND TARGET.DT > '2005-01-01' THEN DELETE;
GO
SELECT * FROM T
SELECT * FROM S
GO
您可以在WHEN NOT MATCHED BY SOURCE
之后设置AND <clause_search_condition>
。
指定有效的搜索条件,然后指定删除与target_table中的行匹配的行。
例如,删除 source.saledate=今天的行。
MERGE SQL_Backup as Target
USING Temp as Source
ON target.code = source.code
WHEN MATCHED THEN update SET
target.saledate = source.saledate,
target.branchcode = source.branchcode
WHEN NOT MATCHED BY TARGET
THEN insert (
code, saledate
)
values (
source.code, source.saledate
)
WHEN NOT MATCHED BY SOURCE AND source.saledate = CONVERT(varchar(100), GETDATE(), 3)
THEN DELETE;
您的销售日期格式是"dd/mm/yy",所以我们需要转换默认的日期格式。
希望对您有所帮助。