3

重複の可能性:
SQL:自己参照テーブルから特定の順序でデータを削除する

SQL Server 2008の自己参照テーブルからレコードのサブセットを削除する必要があります。次のことを実行しようとしていますが、順序が正しくありません。

WITH SelfReferencingTable (ID, depth)
AS
(
   SELECT id, 0 as [depth]
   FROM dbo.Table
   WHERE parentItemID IS NULL AND [t].ColumnA = '123'
   UNION ALL
   SELECT [t].ID, [srt].[depth] + 1 
   FROM dbo.Table t 
   INNER JOIN SelfReferencingTable srt ON [t].parentItemID = [srt].id
   WHERE [t].ColumnA = '123'       
)   
DELETE y FROM dbo.Table y
JOIN SelfReferencingTable x on x.ID = y.id
ORDER BY x.depth DESC

これが機能しない理由はありますか?

4

2 に答える 2

4

特定の順序で削除する必要はありません。

1回の操作ですべて削除するだけです。制約はステートメントの最後でチェックされます。

再帰CTEコードが、削除する必要のあるすべての行を正しく識別していると仮定すると、次のように使用できます。

WITH SelfReferencingTable (ID)
AS
(
   SELECT id
   FROM dbo.Table
   WHERE parentItemID IS NULL AND [t].ColumnA = '123'
   UNION ALL
   SELECT [t].ID 
   FROM dbo.Table t 
   INNER JOIN SelfReferencingTable srt ON [t].parentItemID = [srt].id
   WHERE [t].ColumnA = '123'       
)   
DELETE 
FROM dbo.Table 
WHERE ID IN (SELECT id FROM SelfReferencingTable )
于 2012-09-01T09:33:42.610 に答える
0

句は。deleteを許可しませんorder by。これdeleteは単一のアトミック操作であり、操作のステップがどの順序でdelete完了するかは重要ではありません。

一般的な解決策は、ループ内に依存行がない行を削除することです。

while 1=1
    begin
    delete  yt
    from    YourTable yt
    where   where ColumnA = '123'
            and not exists
            (
            select  *
            from    YourTable yt2
            where   yt2.parentItemId = yt.id
            )

    if @@rowcount = 0
        break
    end
于 2012-08-31T15:33:42.550 に答える