2016-07-29 119 views
0

我正在編寫一個C++應用程序在QT Creator也使用SQLite數據庫連接。我想實現的是,當我從表中刪除一行時,其他表中引用它的行也被刪除。所以在我的情況下,如果我從購物籃中刪除一行,引用來自計算機的行也會被刪除,然後從子系統表,訂戶,法規等等直到最後。之前刪除觸發性能低下

這裏是我的數據庫圖表:每個表

DB Diagram

我創建觸發器與另一個表的外鍵引用。

CREATE TRIGGER delete_fk BEFORE DELETE ON Basket 
FOR EACH ROW BEGIN 
    DELETE FROM Computer WHERE computer.basket = old.id_basket; 
END 

CREATE TRIGGER delete_fk_comp BEFORE DELETE ON computer 
FOR EACH ROW BEGIN 
    DELETE FROM subsystemtable WHERE subsystemtable.computer = id.id_computer; 
END 

CREATE TRIGGER delete_fk_subscriber_map BEFORE DELETE ON subscriber 
FOR EACH ROW BEGIN 
    DELETE FROM mappingtable WHERE mappingtable.subscriber = old.id_subscriber; 
END 

CREATE TRIGGER delete_fk_subscriber_indirect BEFORE DELETE ON subscriber 
FOR EACH ROW BEGIN 
    DELETE FROM indirectsubscriber WHERE indirectsubscriber.subscriber = old.id_subscriber; 
END 

CREATE TRIGGER delete_fk_subscriber BEFORE DELETE ON subscriber 
FOR EACH ROW BEGIN 
    DELETE FROM reserve WHERE reserve.subscriber = old.id_subscriber; 
END 

CREATE TRIGGER delete_fk_subscriber_res BEFORE DELETE ON subscriber 
FOR EACH ROW BEGIN 
    DELETE FROM reserve WHERE reserve.subscriber_res = old.id_subscriber; 
END 

CREATE TRIGGER delete_fk_subs BEFORE DELETE ON subsystem 
FOR EACH ROW BEGIN 
    DELETE FROM subsystemtable WHERE subsystemtable.subsystem = old.id_subsystem; 
END 

CREATE TRIGGER delete_fk_substable_reg BEFORE DELETE ON subsystemtable 
FOR EACH ROW BEGIN 
    DELETE FROM regulations WHERE regulations.subsystem = old.id; 
END 

CREATE TRIGGER delete_fk_substable BEFORE DELETE ON subsystemtable 
FOR EACH ROW BEGIN 
    DELETE FROM subscriber WHERE subscriber.subsystem = old.id; 
END 

我得到了我想要的。它和我想要的完全一樣。但我現在的問題是性能低下。所以在我的數據庫中,每個籃子有大約20臺計算機,每臺計算機大約有5個子系統,每個子系統有100個用戶,等等。當我刪除單個籃子時,整個過程大約需要400毫秒。我應該一次刪除3個籃子,這將需要3秒以上。

我需要找到一種方法,使其工作方式更快。我想大約受到200-300毫秒的限制。我需要關於我該怎麼做的任何建議。

+1

採取一些其他更成熟的數據庫系統?例如PostgreSQL。或者正確使用外鍵,在這裏解釋:https://www.sqlite.org/foreignkeys.html#fk_actions。 'CASCADE'。 – maxik

回答

2

你正在手工實現外鍵。 這不是必需的;您只需使用ON DELETE actions即可讓數據庫執行相應的更改。

無論您是手動實施外鍵還是藉助數據庫,您都需要創建indexes on certain key columns,或者查找相關行所需的所有查找操作都很慢。

+0

具體來說,創建外鍵約束時,應該使用'ON DELETE CASCADE'選項。例如,因爲'Computer'指的是'Basket',所以你應該爲'id_basket'添加一個外鍵常量。然後,如果'Basket'中的一行被刪除,那麼'id_basket'指向的'Computer'中的任何行也會被自動刪除。根本不需要混淆觸發器。 –

+0

由於某些原因,ON DELETE CASCADE不適用於我。看到這個問題:http://stackoverflow.com/questions/38588039/sqlite3-on-delete-cascade-does-not-work。我只能使用SQlite。 @Alvin –

+0

@EgorChubarov:不知道是什麼問題。每次建立到數據庫的新連接時,您確定您正在執行'pragma foreign_keys = on',並且連接到數據庫的所有內容都會執行此編譯指示? –