Angenommen, Sie möchten einen tatsächlichen SQL Server MERGE
Aussage:
MERGE INTO dbo.energydata WITH (HOLDLOCK) AS target
USING dbo.temp_energydata AS source
ON target.webmeterID = source.webmeterID
AND target.DateTime = source.DateTime
WHEN MATCHED THEN
UPDATE SET target.kWh = source.kWh
WHEN NOT MATCHED BY TARGET THEN
INSERT (webmeterID, DateTime, kWh)
VALUES (source.webmeterID, source.DateTime, source.kWh);
Wenn Sie auch Datensätze im Ziel löschen möchten, die nicht in der Quelle sind:
MERGE INTO dbo.energydata WITH (HOLDLOCK) AS target
USING dbo.temp_energydata AS source
ON target.webmeterID = source.webmeterID
AND target.DateTime = source.DateTime
WHEN MATCHED THEN
UPDATE SET target.kWh = source.kWh
WHEN NOT MATCHED BY TARGET THEN
INSERT (webmeterID, DateTime, kWh)
VALUES (source.webmeterID, source.DateTime, source.kWh)
WHEN NOT MATCHED BY SOURCE THEN
DELETE;
Da dies etwas populärer geworden ist, sollte ich diese Antwort ein wenig mit einigen Einschränkungen erweitern, die Sie beachten sollten.
Erstens gibt es mehrere Blogs, die über Parallelitätsprobleme mit MERGE
Erklärung
in älteren Versionen von SQL Server. Ich weiß nicht, ob dieses Problem jemals in späteren Ausgaben behandelt wurde. In jedem Fall kann dies größtenteils durch Angabe von HOLDLOCK
umgangen werden oder SERIALIZABLE
Sperrhinweis:
MERGE INTO dbo.energydata WITH (HOLDLOCK) AS target
[...]
Sie können dasselbe auch mit restriktiveren Transaktionsisolationsstufen erreichen.
Es gibt mehrere andere bekannte Probleme mit MERGE
. (Beachten Sie, dass, da Microsoft Connect vernichtet und Probleme im alten System nicht mit Problemen im neuen System verknüpft hat, diese älteren Probleme schwer aufzuspüren sind. Danke, Microsoft!) Soweit ich das beurteilen kann, sind die meisten von ihnen nicht üblich Probleme oder kann mit denselben Sperrhinweisen wie oben umgangen werden, aber ich habe sie nicht getestet.
So wie es ist, obwohl ich noch nie Probleme mit dem MERGE
hatte -Anweisung selbst verwende ich immer die WITH (HOLDLOCK)
Hinweis, und ich ziehe es vor, die Anweisung nur in den einfachsten Fällen zu verwenden.