2011-08-16 13 views
5

私は4つのテーブルを持っています。最初のテーブルでは主キーとしてappidがあり、他の3つのテーブルではその外部キーがあります。 1つのクエリで3つすべてのデータを削除したい。私はベストを尽くしたが失敗した。誰でも助けることができますか?複数のテーブルから同時にレコードを削除しますか?

+0

これは、解決のために参照アクション「ON DELETE CASCADE」が発明された問題です。 @トニーアンドリュースとは違って、私はそれを一般的な習慣として勧めます。 – onedaywhen

答えて

10

複数のテーブルを参照するdelete文を記述することはできません.4つのdelete文を記述する必要があります。

ただし、必要に応じて、3つの子テーブルの外部キーを "ON DELETE CASCADE"に定義することができます。親テーブルから削除すると、3つの子テーブルの関連する行もすべて削除されます。これは時々役に立ちますが、開発者にとって危険で混乱する可能性があるため、一般的な方法としては推奨しません。

+0

カスケードする外部キーの危険で混乱しやすい性質を詳しく教えてください。私はこの発言に少し驚いているからです。 – Rene

+2

@Rene、それはよく起こります。私は現在、誰かがON DELETE CASCADEとして多くの外部キーを設定したプロジェクトで作業しています。たとえば、ユーザーが 'DELETE order_status_lookup WHERE status_code = 'SHIPPED''のようなことをした場合、それは成功し、ステータス' SHIPPED 'を持つすべての注文も削除されます。私はそれを危険だと呼びます!私は実際にはON DELETE CASCADEを使用しますが、実際には理にかなっています。 –

+0

あなたが言っていることは、それが非常に有用であるかもしれないが間違った方法で使用されるツールが害を引き起こす可能性があるということです。チェーンソーのようなビットはそうではありませんか?しかし、これらの木をすべて手動で切断することをお勧めしますか? – Rene

3

単一のステートメントで多数のテーブルから削除する方法はありませんが、より良い質問は、なぜ同時にすべてのテーブルから削除する必要があるかです。 Oracleでトランザクションがどのように機能するかを完全に理解していないように思えます。

テーブル1から行を削除しても、コミットしないとします。他のすべてのセッションに関する限り、その行は削除されていません。別の接続を開いてその行を照会すると、行はまだそこにあります。

次に、テーブル2,3、および4から順に削除します。依然としてトランザクションをコミットしていないので、データベース上の他のすべてのセッションで削除された行が引き続き表示されます。

次にコミットします。

同時に、他のセッションでは、4つの別々のステートメントで削除を行ったにもかかわらず、4つのテーブルから削除した行が表示されなくなります。

+4

あなたは少し厳しいと思います。 'INSERT ALL'に類似した' DELETE ALL'構文でメリットを見ることができます:従属性を心配することなく、また遅延制約を使わずに、テーブルのセット内のすべての関連レコードをzapするのはすてきです。 (私の必要性は、通常、実稼働環境ではなくテストデータを管理するためです)。 – APC

+0

+1明確で、ポイント・アンサーです。 – Rene

-2

データベースがMysqlの場合、DELETE文でjoinを使用できます。 詳細については、http://dev.mysql.com/doc/refman/5.0/en/delete.htmlを参照してください。

+4

しかし、そうではありません。それはオラクルです。 –

+0

別のコメント(トランザクションまたはカスケードの削除を使用)に加えて、トリガーを使用して子テーブルから削除することもできます。 –

関連する問題