Postgresql
在 Postgresql 中使用“從 … 使用 … where 刪除”時,如何從兩個表或其中至少一個表中刪除數據?
我的 Postgresql 數據庫有這個 sql 腳本:
DELETE FROM table1 USING table2 WHERE table2.frg_table1_id = table1.id AND table1.id = $1
table1
如果滿足條件,我希望它始終刪除數據table1.id = $1
。並且,可選地,也從中刪除相應的數據table2
。即使 對應的數據 intable2
不存在,也必須從中刪除table1
現在的一個問題是,它會從兩個表中刪除數據或從一個表中刪除數據。
我應該如何扭曲我的劇本?
單個
DELETE
語句僅從單個表中刪除行(暫時忽略表繼承)。因此,如果要從兩個表中刪除,則必須執行兩個刪除語句。您可以在“一個”語句中執行此操作,但使用一個公共表表達式,該表達式首先從 table2 中刪除,然後從 table1 中刪除:
with t2_deleted as ( delete from table2 where frg_table1_id = $1 ) delete from table1 where id = $1;
但最終,這與在單個事務中簡單地執行兩個 DELETE 語句完全相同:
delete from table2 where frg_table1_id = $1; delete from table1 where id = $1;
就像@a_horse_with_no_name 所說,如果您需要從 2 個單獨的表中刪除數據,則需要執行 2 個單獨的 SQL 語句。但是您發布的查詢似乎相互依賴。因此,一旦您從Table1中刪除數據,您將失去與Table2匹配的鍵值以進行刪除。
因此,我建議您使用參照完整性或在 Table1 上創建觸發器以同時從 Table2 中刪除匹配的記錄。
這是一個例子。
1. --Create Table1 CREATE TABLE Table1 ( EId int, EName varchar(16) ); 2. --Create Table2 CREATE TABLE Table2 ( EId int, EName varchar(16) ); 3. --Create Trigger Function to DELETE matching records from Table2 CREATE FUNCTION trg_fn_Table1_After_Delete() RETURNS TRIGGER AS $BODY$ BEGIN DELETE FROM Table2 WHERE EId=Old.Eid; RETURN NEW; END $BODY$ LANGUAGE PLPGSQL 4. --Create Trigger on Table1 AFTER DELETE which will execute the function/mathod trg_fn_Table1_After_Delete() CREATE TRIGGER trg_Table1_After_Delete AFTER DELETE ON Table1 FOR EACH ROW EXECUTE PROCEDURE trg_fn_Table1_After_Delete(); ----------------------Insert sample records into Table1 insert into Table1(EId,EName) values('1','Rajesh'); insert into Table1(EId,EName) values('2','Ranjan'); insert into Table1(EId,EName) values('3','Alok Kuwnar'); ---NonMatching Record ----------------------Insert sample records into Table2 insert into Table2(EId,EName) values('1','Rajesh'); insert into Table2(EId,EName) values('2','Ranjan'); insert into Table2(EId,EName) values('4','Ranjan Ranjan');---NonMatching Record ----------------------Validate data select * from Table1; select * from Table2; ---------------------Delete data from Table1 DELETE FROM table1 USING table2 WHERE table2.EId = table1.EId AND Table1.EId=1; ----------------------Re-Validate data select * from Table1; select * from Table2;
謝謝!