8

私は HierarchyID をあまり使用していないので、少しわかりません。テーブルに HierarchyID がある場合、カスケード削除を実行するにはどうすればよいですか? (つまり、「親」を削除するときにすべての「子」を削除します)

CTE と HierarchyID 関数を使用する必要があると思いますが、どうすればよいかわかりません...

4

2 に答える 2

6

トリガーベースのソリューションは次のようになります。

CREATE TRIGGER tr_Hierarchy_DeleteChildren
ON Hierarchy
FOR DELETE
AS
    DELETE FROM Hierarchy
    WHERE ID IN
    (
        SELECT DISTINCT h.ID
        FROM deleted d
        INNER JOIN Hierarchy h
        ON h.ObjectNode.IsDescendantOf(d.ObjectNode) = 1
      EXCEPT
        SELECT ID
        FROM deleted
    )

は、無限のEXCEPT再帰ループに陥らないようにします。私自身の実装では、トリガーが実行されているというコンテキスト情報に実際にフラグを設定し、トリガーの開始時にこのフラグを確認し、フラグがすでに設定されている場合は早期に戻ります。これは必須ではありませんが、パフォーマンスには少し優れています。

または、トリガーを使用したくない場合は、次のロジックをストアドプロシージャに含めることができます。

CREATE PROCEDURE DeleteHierarchyTree
    @ParentID hierarchyid
AS
DELETE FROM Hierarchy
WHERE ID.IsDescendantOf(@ParentID) = 1

最初はずっと簡単に思えますが、人々はこれを使用することを忘れないようにする必要があることに注意してください。トリガーがなく、誰かがDELETESPを経由せずに階層テーブルを直接実行すると、手遅れになるまで誰も知らなくても、子のレコードが非常に簡単に孤立する可能性があります。

于 2010-01-18T20:34:28.417 に答える
4

T-SQLのIsDescendantOfメソッドを確認することをお勧めします。このようなもの:

DECLARE @ParentNodeHID Hierarchyid SET @ParentNodeHID=[削除を開始するノード]

DELETE HierarchyTable WHERE NodeHID.IsDescendantOf(@ParentNodeHID)= 1

(HierarchyTable =階層が保存されているテーブル)

**この方法では、ノードはそれ自体の子と見なされることに注意してください。したがって、@ ParentNodeHIDに渡すものはすべて、WHERE句の条件を満たすことになります。

BOLの記事をご覧ください:ms-help://MS.SQLCC.v10/MS.SQLSVR.v10.en/s10de_6tsql/html/edc80444-b697-410f-9419-0f63c9b5618d.htm

于 2009-10-12T12:25:33.233 に答える