亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

PostgreSQL表分區(qū)的三種方式和操作方法

 更新時間:2025年10月31日 11:21:21   作者:紅燒柯基  
在?PostgreSQL?中,處理數(shù)據(jù)的分區(qū)表的分區(qū)數(shù)量和大小的平衡是一個非常重要的問題,這篇文章主要介紹了PostgreSQL表分區(qū)的三種方式和操作方法,需要的朋友可以參考下

一、什么是表分區(qū)?它和分庫分表有什么區(qū)別?

1.1 什么是表分區(qū)(Table Partitioning)?

表分區(qū)是數(shù)據(jù)庫的一種物理設(shè)計技術(shù),它將一個大表從邏輯上視為一個整體,但從物理上拆分成多個子表(分區(qū)),每個分區(qū)存儲一部分數(shù)據(jù)。

  • 邏輯上:你仍然像操作一張表一樣查詢它
  • 物理上:數(shù)據(jù)分散在多個子表中,按規(guī)則存儲
  • ? 舉個例子:
    jgpt_jzd_test 按年份拆成 p2023、p2024p2025 三個分區(qū),查詢時仍用 SELECT * FROM jgpt_jzd_test,但數(shù)據(jù)庫只掃描相關(guān)分區(qū)。

1.2 表分區(qū) vs 分庫分表:關(guān)鍵區(qū)別

對比項表分區(qū)分庫分表
實現(xiàn)層級數(shù)據(jù)庫內(nèi)部(單庫)應(yīng)用層或中間件(跨庫)
透明性高(應(yīng)用無感知)低(需改代碼)
管理復(fù)雜度低(自動路由)高(需路由規(guī)則)
事務(wù)支持完整支持跨庫事務(wù)復(fù)雜
適用場景單表過大(百萬~億級)數(shù)據(jù)量極大(TB級+)
技術(shù)棧PostgreSQL、MySQL 8.0+ShardingSphere、MyCat

? 簡單說

  • 表分區(qū)是“數(shù)據(jù)庫幫你拆”
  • 分庫分表是“你自己寫代碼拆”

二、表分區(qū)的優(yōu)缺點與使用場景

優(yōu)點

優(yōu)勢說明
查詢性能提升分區(qū)剪枝(Partition Pruning)自動跳過無關(guān)分區(qū)
數(shù)據(jù)管理高效刪除舊數(shù)據(jù)從 DELETE 變?yōu)?nbsp;DROP PARTITION(秒級)
維護更方便可對單個分區(qū)做 VACUUM、ANALYZE、備份
I/O 分散不同分區(qū)可分布到不同磁盤(高級用法)

缺點

缺點說明
全表掃描變慢需掃描所有分區(qū),元數(shù)據(jù)開銷增加
分區(qū)鍵固定一旦選定(如 gmt_create),不能更改
管理復(fù)雜度上升需定期創(chuàng)建新分區(qū)
不支持主鍵跨分區(qū)主鍵必須包含分區(qū)鍵

三、PostgreSQL 表分區(qū)的三種方式

PostgreSQL 支持三種分區(qū)策略:

1.Range 分區(qū)(按范圍)

  • 適用:時間、數(shù)值范圍
  • 示例:按 gmt_create 按年/月分區(qū)
  • 語法

    PARTITION BY RANGE (gmt_create)

2.List 分區(qū)(按枚舉值)

  • 適用:固定分類,如省份、狀態(tài)
  • 示例:按 province 分區(qū)
  • 語法

    PARTITION BY LIST (province)

3.Hash 分區(qū)(按哈希值)

  • 適用:數(shù)據(jù)均勻分布,無明顯查詢模式
  • 示例:按 id 哈希分 4 份
  • 語法

    PARTITION BY HASH (id)

四、實戰(zhàn):jgpt_jzd_test表分區(qū)操作全流程

將 3000 萬+ 的 jgpt_jzd_test 表改造為按年分區(qū)的分區(qū)表。

步驟 1:創(chuàng)建分區(qū)主表

-- 創(chuàng)建主表(邏輯表,不存數(shù)據(jù))
CREATE TABLE jgpt_jzd_test_partitioned (
    id                    varchar(32),
    jzdbh                 varchar(255),
    xzb                   varchar(255),
    yzb                   varchar(255),
    htxxid                varchar(255),
    gmt_create            timestamp(6) NOT NULL,  -- 必須 NOT NULL
    gmt_modified          timestamp(6),
    del_flag              varchar,
    created_user_id       varchar(255),
    created_user          varchar(255),
    last_modified_user_id varchar(255),
    last_modified_user    varchar(255),
    dkh                   varchar(255),
    dkms                  varchar(255),
    batchnum              varchar(255)
) PARTITION BY RANGE (gmt_create);

步驟 2:創(chuàng)建子分區(qū)(按年)

-- 2023 年分區(qū)
CREATE TABLE jgpt_jzd_test_p2023 
    PARTITION OF jgpt_jzd_test_partitioned
    FOR VALUES FROM ('2023-01-01') TO ('2024-01-01');

-- 2024 年分區(qū)
CREATE TABLE jgpt_jzd_test_p2024 
    PARTITION OF jgpt_jzd_test_partitioned
    FOR VALUES FROM ('2024-01-01') TO ('2025-01-01');

-- 2025 年分區(qū)
CREATE TABLE jgpt_jzd_test_p2025 
    PARTITION OF jgpt_jzd_test_partitioned
    FOR VALUES FROM ('2025-01-01') TO ('2026-01-01');

步驟 3:遷移數(shù)據(jù)

-- 從舊表插入到新分區(qū)表(自動路由)
INSERT INTO jgpt_jzd_test_partitioned 
SELECT * FROM jgpt_jzd_test;

步驟 4:創(chuàng)建索引

-- 在主表創(chuàng)建索引,所有分區(qū)自動繼承
CREATE INDEX idx_jgpt_jzd_test_htxxid ON jgpt_jzd_test_partitioned (htxxid);

步驟 5:切換表名(原子操作)

-- 1. 備份原表
ALTER TABLE jgpt_jzd_test RENAME TO jgpt_jzd_test_backup;

-- 2. 新表啟用原名
ALTER TABLE jgpt_jzd_test_partitioned RENAME TO jgpt_jzd_test;

? 至此,jgpt_jzd_test 已是分區(qū)表!

五、驗證表分區(qū)是否成功

1. 查看分區(qū)結(jié)構(gòu)

-- 查詢系統(tǒng)表
SELECT 
    inhrelid::regclass AS child_table,
    inhparent::regclass AS parent_table
FROM pg_inherits 
WHERE inhparent = 'jgpt_jzd_test'::regclass;

2. 驗證分區(qū)剪枝是否生效

explain SELECT COUNT(*) FROM jgpt_jzd_test WHERE gmt_create >= '2025-01-01' AND gmt_create < '2026-01-01';

可以看到只查詢了jgpt_jzd_test_p2025一張分區(qū)表

六、安全刪除分區(qū):DETACHvsDROP(關(guān)鍵區(qū)別)

在表分區(qū)的日常維護中,刪除歷史數(shù)據(jù)是一個高頻操作。PostgreSQL 提供了兩種方式來“移除”分區(qū),但它們的安全性、可逆性和使用場景完全不同。

我們以 jgpt_jzd_test_p2024 分區(qū)為例,對比兩種操作:

1.DETACH PARTITION—— 安全的“解綁”操作

ALTER TABLE jgpt_jzd_test_partitioned
    DETACH PARTITION jgpt_jzd_test_p2024;

操作特點:

  • 數(shù)據(jù)不會丟失!jgpt_jzd_test_p2024 表變成一個獨立的普通表
  • 主表 jgpt_jzd_test_partitioned 不再包含該分區(qū)的數(shù)據(jù)
  • 可隨時對 jgpt_jzd_test_p2024 進行查詢、導(dǎo)出、備份或重新掛載

適用場景:

  • 需要歸檔數(shù)據(jù)
  • 刪除前做審計或備份
  • 不確定是否永久刪除
-- 確認無誤后,再刪除
DROP TABLE jgpt_jzd_test_p2024;

? 推薦做法先 DETACH,再 DROP,避免誤刪。

2.DROP PARTITION—— 永久刪除

ALTER TABLE jgpt_jzd_test_partitioned
    DROP PARTITION jgpt_jzd_test_p2024;

操作特點:

  • 數(shù)據(jù)立即永久丟失!無法通過 DROP 回滾
  • 相當于執(zhí)行了 DROP TABLE,文件被物理刪除
  • 無法恢復(fù)(除非有數(shù)據(jù)庫備份)

適用場景:

  • 確認數(shù)據(jù)不再需要
  • 緊急釋放磁盤空間
  • 自動化腳本中已確認安全

對比總結(jié)

操作數(shù)據(jù)是否保留是否可逆安全性推薦使用場景
DETACH PARTITION? 保留? 可逆所有刪除操作的首選
DROP PARTITION? 丟失? 不可逆確認永久刪除

七、自己的理解

1.表分區(qū)之后,你在datagrip或navicat里面看到的還是一張表,數(shù)據(jù)也都在這張表里,但實際上這張表是主表,沒有存儲數(shù)據(jù)。

2.數(shù)據(jù)實際存儲在分區(qū)表里,例如jgpt_jzd_test_p2024,因此代碼里面是可以直接調(diào)用這張表的

3.平時基本不用管分區(qū)表,正常使用主表就行了,比如你插入數(shù)據(jù),直接往jgpt_jzd_test插入,數(shù)據(jù)庫會根據(jù)你的gmt字段自動插入到相應(yīng)的分區(qū)表里面,平時使用基本是無感的

總結(jié):我的認知升級

舊認知新認知
分區(qū)就是“拆表”分區(qū)是“邏輯統(tǒng)一,物理分離”
數(shù)據(jù)存在主表主表是“空殼”,數(shù)據(jù)在分區(qū)
只能查主表可直查分區(qū),性能更優(yōu)
分區(qū)很復(fù)雜日常使用完全無感

到此這篇關(guān)于PostgreSQL表分區(qū)的三種方式和操作方法的文章就介紹到這了,更多相關(guān)PostgreSQL表分區(qū)內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

最新評論