当前位置: 首页 > news >正文

PostgreSQL分区表:基础语法与运维实践

引言

简介:什么是数据库分区

数据库分区是一种将大型表物理上分割成多个较小的部分的技术。每个部分称为一个分区,这些分区可以分布在不同的存储设备上,以提高查询性能和管理效率。

为什么使用分区表

  • 提高查询性能:通过减少需要扫描的数据量,查询速度可以显著提升。
  • 简化数据管理:分区使得数据的备份、恢复和归档更加容易。
  • 优化存储:可以将不同分区放在不同的存储介质上,以平衡性能和成本。
  • 增强可维护性:分区表的维护操作(如索引重建、数据清理)可以逐分区进行,减少对整个系统的干扰。

PostgreSQL中的分区支持概述

PostgreSQL从9.0版本开始引入了分区支持,并在后续版本中不断改进。目前,PostgreSQL支持多种分区类型,包括范围分区、列表分区和散列分区。通过这些分区技术,可以有效地管理和优化大规模数据表。

分区类型

范围分区(Range Partitioning)

范围分区是根据一个或多个列的值范围来划分表。例如,可以根据日期或数值范围来创建分区。

示例

CREATE TABLE sales (id SERIAL ,sale_date DATE NOT NULL,amount NUMERIC,PRIMARY KEY (id,sale_date)
) PARTITION BY RANGE (sale_date);CREATE TABLE sales_2022 PARTITION OF sales FOR VALUES FROM ('2022-01-01') TO ('2022-12-31');
CREATE TABLE sales_2023 PARTITION OF sales FOR VALUES FROM ('2023-01-01') TO ('2023-12-31');

这个语句创建了一个名为 sales 的表,该表有三个字段:id(一个自动递增的主键)、sale_date(一个非空的日期字段)和 amount(一个数值字段)。重要的是,这个表被声明为一个分区表,基于 sale_date 字段的范围进行分区。并创建了 sales 表的两个分区子表:sales_2022 和 sales_2023。每个子表都负责存储 sales 表中特定日期范围内的数据。其中,sales_2022 存储 sale_date 从 2022-01-01 到 2022-12-31 的数据,sales_2023 存储 sale_date 从 2023-01-01 到 2023-12-31 的数据。

列表分区(List Partitioning)

列表分区是根据一个或多个列的具体值来划分表。适用于列值有限且已知的情况。

示例

CREATE TABLE employees (id SERIAL ,department VARCHAR(50) NOT NULL,name VARCHAR(100),PRIMARY KEY (id,department)
) PARTITION BY LIST (department);CREATE TABLE employees_sales PARTITION OF employees FOR VALUES IN ('Sales');
CREATE TABLE employees_marketing PARTITION OF employees FOR VALUES IN ('Marketing');

这个语句创建了一个名为 employees 的表,该表有三个字段:id(一个自动递增的主键)、department(一个非空的 VARCHAR 类型字段,用于存储部门名称)和 name(一个 VARCHAR 类型字段,用于存储员工姓名)。这个表被声明为一个分区表,基于 department 字段的列表值进行分区。并创建了 employees 表的两个分区子表:employees_sales 和 employees_marketing。employees_sales 负责存储 department 字段值为 ‘Sales’ 的员工数据,而 employees_marketing 负责存储 department 字段值为 ‘Marketing’ 的员工数据。

散列分区(Hash Partitioning)

散列分区是根据列值的哈希函数结果来划分表。适用于需要均匀分布数据的情况。

示例

CREATE TABLE users (id SERIAL PRIMARY KEY,username VARCHAR(50) NOT NULL,email VARCHAR(100)
) PARTITION BY HASH (id);CREATE TABLE users_0 PARTITION OF users FOR VALUES WITH (MODULUS 4, REMAINDER 0);
CREATE TABLE users_1 PARTITION OF users FOR VALUES WITH (MODULUS 4, REMAINDER 1);
CREATE TABLE users_2 PARTITION OF users FOR VALUES WITH (MODULUS 4, REMAINDER 2);
CREATE TABLE users_3 PARTITION OF users FOR VALUES WITH (MODULUS 4, REMAINDER 3);

这个语句创建了一个名为 users 的表,该表有三个字段:id(一个自动递增的主键)、username(一个非空的 VARCHAR 类型字段,用于存储用户名)和 email(一个 VARCHAR 类型字段,用于存储电子邮件地址)。这个表被声明为一个分区表,基于 id 字段的哈希值进行分区。并创建了 users 表的四个分区子表。这些子表根据 id 字段的哈希值进行分区,具体使用了模运算(MODULUS)和余数(REMAINDER)来确定数据应该存储在哪个分区中。

  • users_0 存储 id 哈希值模 4 余 0 的数据。

  • users_1 存储 id 哈希值模 4 余 1 的数据。

  • users_2 存储 id 哈希值模 4 余 2 的数据。

  • users_3 存储 id 哈希值模 4 余 3 的数据。

创建分区表

基本语法

创建分区表的基本语法如下:

CREATE TABLE table_name (column1 data_type,column2 data_type,...
) PARTITION BY {RANGE | LIST | HASH} (column_name);

范围分区示例

CREATE TABLE orders (order_id SERIAL ,order_date DATE NOT NULL,amount NUMERIC,PRIMARY KEY(order_id,order_date)
) PARTITION BY RANGE (order_date);CREATE TABLE orders_2022 PARTITION OF orders FOR VALUES FROM ('2022-01-01') TO ('2022-12-31');
CREATE TABLE orders_2023 PARTITION OF orders FOR VALUES FROM ('2023-01-01') TO ('2023-12-31');

列表分区示例

CREATE TABLE products (product_id SERIAL,category VARCHAR(50) NOT NULL,name VARCHAR(100)PRIMARY KEY(product_id,category)
) PARTITION BY LIST (category);CREATE TABLE products_electronics PARTITION OF products FOR VALUES IN ('Electronics');
CREATE TABLE products_clothing PARTITION OF products FOR VALUES IN ('Clothing');

散列分区示例

CREATE TABLE customers (customer_id SERIAL PRIMARY KEY,name VARCHAR(100),email VARCHAR(100)
) PARTITION BY HASH (customer_id);CREATE TABLE customers_0 PARTITION OF customers FOR VALUES WITH (MODULUS 4, REMAINDER 0);
CREATE TABLE customers_1 PARTITION OF customers FOR VALUES WITH (MODULUS 4, REMAINDER 1);
CREATE TABLE customers_2 PARTITION OF customers FOR VALUES WITH (MODULUS 4, REMAINDER 2);
CREATE TABLE customers_3 PARTITION OF customers FOR VALUES WITH (MODULUS 4, REMAINDER 3);

注意事项

  • 分区键的选择:选择合适的分区键是关键。分区键应具有高选择性,且能够均匀分布数据。
  • 分区策略的设计:根据业务需求和数据特性设计合理的分区策略。例如,* 对于时间序列数据,范围分区通常是最佳选择。

管理分区表

添加新分区

--创建分区表
CREATE TABLE orders_2024 (order_id SERIAL ,order_date DATE NOT NULL,amount NUMERIC,PRIMARY KEY(order_id,order_date)
) ;
--将分区表追加到主表
ALTER TABLE orders ATTACH PARTITION orders_2024 FOR VALUES FROM ('2024-01-01') TO ('2024-12-31');

删除分区

ALTER TABLE orders DETACH PARTITION orders_2022;
DROP TABLE orders_2022;

修改现有分区

1. 重命名分区

ALTER TABLE orders RENAME PARTITION orders_2022 TO orders_2022_old;

2.修改分区范围

ALTER TABLE orders DETACH PARTITION orders_2022;
ALTER TABLE orders ATTACH PARTITION orders_2022 FOR VALUES FROM ('2022-01-01') TO ('2022-06-30');

需要注意的是,修改分区范围可能会影响数据的完整性和查询结果,因为该分区现在只包含指定日期范围内的数据。如果原始 orders_2022 分区包含超出此范围的数据,则这些数据在重新附加后将不再作为 orders 表的一部分。

分区维护的最佳实践

  • 定期检查和优化:定期检查分区表的性能和存储情况,必要时进行优化。
  • 数据归档:及时归档不再需要的历史数据,释放存储空间。
  • 监控和日志:启用监控和日志记录,以便及时发现和解决问题。

查询优化

如何利用分区提高查询性能

  • 减少扫描范围:查询时,数据库引擎只扫描相关的分区,而不是整个表,从而减少I/O操作。
  • 并行处理:多个分区可以并行处理,提高查询速度。
  • 索引优化:在每个分区上创建局部索引,可以进一步提高查询性能。

使用EXPLAIN分析查询计划

EXPLAIN命令可以帮助你理解查询的执行计划,从而优化查询性能。

EXPLAIN SELECT * FROM sales WHERE sale_date BETWEEN '2022-01-01' AND '2022-12-31';

通过查看输出,你可以看到哪些分区被扫描,以及查询的执行步骤。

索引在分区表中的作用

1,局部索引:在每个分区上创建索引,适用于大多数查询场景。
2,全局索引:跨所有分区创建索引,适用于需要跨分区查询的场景。

数据迁移与维护

将现有表转换为分区表

创建分区表结构:

CREATE TABLE sales_new (id SERIAL PRIMARY KEY,sale_date DATE NOT NULL,amount NUMERIC
) PARTITION BY RANGE (sale_date);

创建分区:

CREATE TABLE sales_2022 PARTITION OF sales_new FOR VALUES FROM ('2022-01-01') TO ('2022-12-31');
CREATE TABLE sales_2023 PARTITION OF sales_new FOR VALUES FROM ('2023-01-01') TO ('2023-12-31');

迁移数据:

INSERT INTO sales_new SELECT * FROM sales WHERE sale_date BETWEEN '2022-01-01' AND '2022-12-31';
INSERT INTO sales_new SELECT * FROM sales WHERE sale_date BETWEEN '2023-01-01' AND '2023-12-31';

切换表名:

BEGIN;
ALTER TABLE sales RENAME TO sales_old;
ALTER TABLE sales_new RENAME TO sales;
COMMIT;

分区表的数据导入导出

数据导入:

COPY sales_2022 FROM '/path/to/sales_2022.csv' CSV HEADER;
COPY sales_2023 FROM '/path/to/sales_2023.csv' CSV HEADER;

数据导出:

COPY (SELECT * FROM sales WHERE sale_date BETWEEN '2022-01-01' AND '2022-12-31') TO '/path/to/sales_2022.csv' CSV HEADER;
COPY (SELECT * FROM sales WHERE sale_date BETWEEN '2023-01-01' AND '2023-12-31') TO '/path/to/sales_2023.csv' CSV HEADER;

定期维护和检查分区表

  • 定期检查分区:确保分区的完整性和一致性。
  • 索引维护:定期重建索引,以保持查询性能。
  • 数据清理:定期删除不再需要的历史数据。

监控与故障排除

监控分区表的性能指标

  • 查询性能:使用EXPLAIN和EXPLAIN ANALYZE分析查询性能。
  • I/O性能:监控磁盘I/O操作,确保分区表的I/O负载均衡。
  • 锁争用:监控锁争用情况,避免因锁导致的性能瓶颈。

常见问题及解决方法

  • 查询性能下降:检查查询计划,优化索引和分区策略。
  • 数据不一致:定期检查数据完整性,修复损坏的分区。
  • 磁盘空间不足:及时归档历史数据,释放存储空间。

分区表的优势总结

  • 提高查询性能:通过减少扫描范围和并行处理,显著提升了查询速度。
  • 简化数据管理:分区使得数据的备份、恢复和归档更加容易。
  • 优化存储:可以将不同分区放在不同的存储介质上,平衡性能和成本。
  • 增强可维护性:分区表的维护操作可以逐分区进行,减少对整个系统的干扰。

分区表作为PostgreSQL的一项重要特性,为大数据管理和查询提供了有效的解决方案。通过合理地使用分区表,可以提高查询效率、简化数据备份和恢复操作,并提高系统的可维护性和可扩展性。对于数据库管理员和开发者来说,掌握分区表的基础语法和运维实践将是提升数据库性能和管理效率的关键。

通过本文的阅读,能够深入了解PostgreSQL分区表的概念、优势以及基础语法和运维实践,为构建高效、可扩展的数据库系统提供有力的支持。

相关文章:

PostgreSQL分区表:基础语法与运维实践

引言 简介:什么是数据库分区 数据库分区是一种将大型表物理上分割成多个较小的部分的技术。每个部分称为一个分区,这些分区可以分布在不同的存储设备上,以提高查询性能和管理效率。 为什么使用分区表 提高查询性能:通过减少需…...

Docker入门系列——DockerFile的使用

前面了解了Docker的基本概念,今天来认识一下DockerFile。 Dockerfile 是一个文本文件,包含一系列指令来组装 Docker 镜像。每个指令执行一个特定动作,例如安装包、复制文件或定义启动命令。正确使用 Dockerfile 指令对于构建高效容器至关重要…...

数据集平台分享

Kaggle: Your Machine Learning and Data Science CommunityKaggle is the world’s largest data science community with powerful tools and resources to help you achieve your data science goals.https://www.kaggle.com/Kaggle 包含非常丰富的数据集和代码,…...

去地面算法——depth_clustering算法调试(1)

1 源码下载 论文: 《2016-Fast Range Image-Based Segmentation of Sparse 3D Laser Scans for Online Operation》 《2017-Efficient Online Segmentation for Sparse 3D Laser Scans》 代码:git链接 2 问题记录 2.1 无法找到qt问题 问题截图&…...

设计模式-七个基本原则之一-单一职责原则 + SpringBoot案例

单一职责原理:(SRP) 面向对象七个基本原则之一 清晰的职责:每个类应该有一个明确的职责,避免将多个责任混合在一起。降低耦合:通过将不同的职责分开,可以降低类之间的耦合度,提高系统的灵活性。易于维护:当…...

HWA高速辅助驾驶系统组成及功能场景

HWA最基本功能包括智能跟车、拨杆变道、压速变道、车道居中保持等功能,有效减轻驾驶疲劳。随着智能驾驶不断走向成熟,HWA升级到高速自动驾驶HWP,可实现智能避让汇入口、智能避让大车、分心/疲劳监测、智能进出匝道、智能判别易混分叉路口、智…...

SpringMVC学习笔记(一)

一、SpringMVC的基本概念 (一)三层架构和MVC 1、三层架构概述 我们的开发架构一般都是基于两种形式,一种是 C/S 架构,也就是客户端/服务器,另一种是 B/S 架构,也就是浏览器服务器。在 JavaEE 开发中&…...

kaggle 如何利用API下载数据集

首先 上传kaggle官网生成得 API 密钥: kaggle.json 文件。放到该代码同目录下,再运行一下代码。 注: 只需要修改下载竞赛数据集,就可以选择你的指定数据集。 jupyter文件运行 #首先 上传 kaggle.json 文件并设置 API 密钥 #再…...

第一个 Flutter 项目(1)共46节

前端开发工具vs code,安装Flutter sdk,如果你的下载速度比较慢,可以选择这个😄 flutter sdk 解压码:stwq 配置可以看这Flutter 新建工程一直等待 解决办法-CSDN博客 如果你是新的 Flutter 开发者,我们建…...

学术论文写作丨机器学习与深度学习

目录 第一章、ChatGPT-4o使用方法与技巧 第二章、ChatGPT-4o辅助文献检索、总结与分析 第三章、ChatGPT-4o辅助学术论文选题、创新点挖掘与实验方案设计 第四章、ChatGPT-4o辅助学术论文开题与大纲生成 第五章、ChatGPT-4o辅助学术论文写作马拉松活动介绍 第六章、ChatGP…...

导-4涉及的知识点

除了本课题,3D结构几何修复领域还有以下一些值得关注的研究: 1. **Poisson图像编辑**: 成功地将给定的纹理块融合到可能完全不同的背景图像上。 2. **张量投票(TV)框架**: - 讨论了使用张量投票框架进…...

从0开始深度学习(28)——序列模型

序列模型是指一类特别设计来处理序列数据的神经网络模型。序列数据指的是数据中的每个元素都有先后顺序,比如时间序列数据(股票价格、天气变化等)、自然语言文本(句子中的单词顺序)、语音信号等。 1 统计工具 前面介绍…...

vue2使用 <component> 标签动态渲染不同的表单组件

在后台管理系统中,涉及到大量表单信息的修改和新增。现在想对模板中代码做一些简单的优化。 1. 使用 v-for 循环简化表单项 可以将表单项的定义提取到一个数组中,然后使用 v-for 循环来生成这些表单项。这将减少重复代码,提高可维护性。 2…...

C#实现在windows上实现指定句柄窗口的指定窗口坐标点击鼠标左键和右键的详细情况

在Windows编程中,有时我们需要对特定窗口进行操作,比如模拟鼠标点击。这在自动化测试、脚本编写或某些特定应用程序的开发中尤为常见。本文将深入探讨如何在C#中实现对指定句柄窗口进行鼠标点击操作,包括左键和右键点击。我们会从理论背景开始…...

探索Python自动化新境界:Invoke库的神秘面纱

文章目录 **探索Python自动化新境界:Invoke库的神秘面纱**第一部分:背景介绍第二部分:Invoke库是什么?第三部分:如何安装Invoke库?第四部分:Invoke库函数使用方法1. 定义任务2. 执行任务3. 任务…...

CSS样式实现3D效果

CSS 3D效果是通过CSS3中的transform和perspective等属性来实现的。这些属性允许你创建具有深度感和三维外观的网页元素。以下是一些常见的CSS 3D效果及其实现方法: 1. 3D旋转(Rotate) 使用transform: rotateX(), rotateY(), rotateZ()来分别…...

华为eNSP:MSTP

一、什么是MSTP? 1、MSTP是IEEE 802.1S中定义的生成树协议,MSTP兼容STP和RSTP,既可以快速收敛,也提供了数据转发的多个冗余路径,在数据转发过程中实现VLAN数据的负载均衡。 2、MSTP可以将一个或多个VLAN映射到一个Inst…...

modbus协议 Mthings模拟器使用

进制转换 HEX 16进制 (0、1、2、3、4、5、6、7、8、9、A、B、C、D、E、F表示0-15) dec 10进制 n(16进制) -> 10 abcd.efg(n) d*n^0 c*n^1 b*n^2 a*n^3 e*n^-1 f*n^-2 g*n^-3(10) 10 -> n(16进制) Modbus基础概念 高位为NUM_H&…...

内网安全-代理技术-socket协议

小迪安全网络架构图: 背景:当前获取window7 出网主机的shell。 1.使用msf上线,查看路由 run autoroute -p 添加路由: run post/multi/manage/autoroute 使用socks模块开启节点,作为流量跳板 msf6 exploit(multi/ha…...

选择排序(C语言)

一、步骤 选择排序的基本思想:每一次从待排序的数据元素中选出最小(或最大)的一个元素,存放在序列的起始位置,直到全部待排序的数据元素排完 。 1.首先,我们先建立一个乱序数组,如&#xff1…...

eNSP-Cloud(实现本地电脑与eNSP内设备之间通信)

说明: 想象一下,你正在用eNSP搭建一个虚拟的网络世界,里面有虚拟的路由器、交换机、电脑(PC)等等。这些设备都在你的电脑里面“运行”,它们之间可以互相通信,就像一个封闭的小王国。 但是&#…...

零门槛NAS搭建:WinNAS如何让普通电脑秒变私有云?

一、核心优势:专为Windows用户设计的极简NAS WinNAS由深圳耘想存储科技开发,是一款收费低廉但功能全面的Windows NAS工具,主打“无学习成本部署” 。与其他NAS软件相比,其优势在于: 无需硬件改造:将任意W…...

地震勘探——干扰波识别、井中地震时距曲线特点

目录 干扰波识别反射波地震勘探的干扰波 井中地震时距曲线特点 干扰波识别 有效波:可以用来解决所提出的地质任务的波;干扰波:所有妨碍辨认、追踪有效波的其他波。 地震勘探中,有效波和干扰波是相对的。例如,在反射波…...

python打卡day49

知识点回顾: 通道注意力模块复习空间注意力模块CBAM的定义 作业:尝试对今天的模型检查参数数目,并用tensorboard查看训练过程 import torch import torch.nn as nn# 定义通道注意力 class ChannelAttention(nn.Module):def __init__(self,…...

【位运算】消失的两个数字(hard)

消失的两个数字(hard) 题⽬描述:解法(位运算):Java 算法代码:更简便代码 题⽬链接:⾯试题 17.19. 消失的两个数字 题⽬描述: 给定⼀个数组,包含从 1 到 N 所有…...

UDP(Echoserver)

网络命令 Ping 命令 检测网络是否连通 使用方法: ping -c 次数 网址ping -c 3 www.baidu.comnetstat 命令 netstat 是一个用来查看网络状态的重要工具. 语法:netstat [选项] 功能:查看网络状态 常用选项: n 拒绝显示别名&#…...

C++ 基础特性深度解析

目录 引言 一、命名空间(namespace) C 中的命名空间​ 与 C 语言的对比​ 二、缺省参数​ C 中的缺省参数​ 与 C 语言的对比​ 三、引用(reference)​ C 中的引用​ 与 C 语言的对比​ 四、inline(内联函数…...

以光量子为例,详解量子获取方式

光量子技术获取量子比特可在室温下进行。该方式有望通过与名为硅光子学(silicon photonics)的光波导(optical waveguide)芯片制造技术和光纤等光通信技术相结合来实现量子计算机。量子力学中,光既是波又是粒子。光子本…...

VisualXML全新升级 | 新增数据库编辑功能

VisualXML是一个功能强大的网络总线设计工具,专注于简化汽车电子系统中复杂的网络数据设计操作。它支持多种主流总线网络格式的数据编辑(如DBC、LDF、ARXML、HEX等),并能够基于Excel表格的方式生成和转换多种数据库文件。由此&…...

相关类相关的可视化图像总结

目录 一、散点图 二、气泡图 三、相关图 四、热力图 五、二维密度图 六、多模态二维密度图 七、雷达图 八、桑基图 九、总结 一、散点图 特点 通过点的位置展示两个连续变量之间的关系,可直观判断线性相关、非线性相关或无相关关系,点的分布密…...