Postgresql
將幾張大表拆分成多張,避免空表
我正在重組和統一 PostgreSQL 中的大型數據庫。其中一部分是根據它們在“鍵”中的值將一些大表拆分為較小的表。我為此編寫的函式執行良好,如下所示:
CREATE OR REPLACE FUNCTION split_tables (table_string varchar(100)) RETURNS void AS $$ DECLARE r_row record; BEGIN FOR r_row IN SELECT type FROM type_list LOOP EXECUTE 'CREATE TABLE public.id_' || table_string || '__' || r_row.type || ' AS (SELECT * FROM id_' || table_string || ' WHERE lower(id_' || table_string || '.key) = lower(''' || r_row.type || '''));'; END LOOP; END; $$ LANGUAGE plpsql;
因此,這將遍歷 type_list 中的所有條目並為每種類型創建表。要對所有需要拆分的表執行此操作,我將此函式稱為
SELECT tobesplit.id FROM tobesplit, LATERAL split_tables(tobseplit.id);
但是,這會為 type_list 中的所有條目創建表,即使表中沒有要為某些類型拆分的條目。所以最後,我創建了一大堆我不需要的空表。我尋找了僅在結果不為空時才創建表的方法,並在以下答案中找到了可能的解決方案:CREATE TABLE IF ONLY NOT EMPTY RESULT SET。
如果我單獨測試它,這會起作用,但我不知道如何將它合併到執行語句中。一旦我將 IF 或 CASE 子句寫入 EXECUTE 語句,我總是會遇到語法錯誤。
我很感謝任何想法:)
你可以改變
FOR r_row IN SELECT type FROM type_list
到
FOR r_row IN EXECUTE format( 'SELECT DISTINCT lower(key) AS type FROM %I', 'id_' || table_string )
我建議您使用列表分區並將所有不存在的鍵集中到一個分區中。