位置: 编程技术 - 正文

PostgreSQL教程(三):表的继承和分区表详解

编辑:rootadmin

推荐整理分享PostgreSQL教程(三):表的继承和分区表详解,希望有所帮助,仅作参考,欢迎阅读内容。

文章相关热门搜索词:,内容如对您有帮助,希望把文章链接给更多的朋友!

一、表的继承:

这个概念对于很多已经熟悉其他数据库编程的开发人员而言会多少有些陌生,然而它的实现方式和设计原理却是简单易懂,现在就让我们从一个简单的例子开始吧。 1. 第一个继承表: capitals表继承自cities表的所有属性。在PostgreSQL里,一个表可以从零个或多个其它表中继承属性,而且一个查询既可以引用父表中的所有行,也可以引用父表的所有行加上其所有子表的行,其中后者是缺省行为。 如果希望只从父表中提取数据,则需要在SQL中加入ONLY关键字,如: 上例中cities前面的"ONLY"关键字表示该查询应该只对cities进行查找而不包括继承级别低于cities的表。许多我们已经讨论过的命令--SELECT,UPDATE和DELETE--支持这个"ONLY"符号。 在执行整表数据删除时,如果直接truncate父表,此时父表和其所有子表的数据均被删除,如果只是truncate子表,那么其父表的数据将不会变化,只是子表中的数据被清空。 2. 确定数据来源: 有时候你可能想知道某条记录来自哪个表。在每个表里我们都有一个系统隐含字段tableoid,它可以告诉你表的来源: 以上的结果只是给出了tableoid,仅仅通过该值,我们还是无法看出实际的表名。要完成此操作,我们就需要和系统表pg_class进行关联,以通过tableoid字段从该表中提取实际的表名,见以下查询: 3. 数据插入的注意事项: 继承并不自动从INSERT或者COPY中向继承级别中的其它表填充数据。在我们的例子里,下面的INSERT语句不会成功: 我们可能希望数据被传递到capitals表里面去,但是这是不会发生的:INSERT总是插入明确声明的那个表。 4. 多表继承: 一个表可以从多个父表继承,这种情况下它拥有父表们的字段的总和。子表中任意定义的字段也会加入其中。如果同一个字段名出现在多个父表中,或者同时出现在父表和子表的定义里,那么这些字段就会被"融合",这样在子表里面就只有一个这样的字段。要想融合,字段必须是相同的数据类型,否则就会抛出一个错误。融合的字段将会拥有它所继承的字段的所有约束。 5. 继承和权限:

表访问权限并不会自动继承。因此,一个试图访问父表的用户还必须具有访问它的所有子表的权限,或者使用ONLY关键字只从父表中提取数据。在向现有的继承层次添加新的子表的时候,请注意给它赋予所有权限。 继承特性的一个严重的局限性是索引(包括唯一约束)和外键约束只施用于单个表,而不包括它们的继承的子表。这一点不管对引用表还是被引用表都是事实,因此在上面的例子里,如果我们声明cities.name为UNIQUE或者是一个PRIMARY KEY,那么也不会阻止capitals表拥有重复了名字的cities数据行。 并且这些重复的行缺省时在查询cities表的时候会显示出来。实际上,缺省时capitals将完全没有唯一约束,因此可能包含带有同名的多个行。你应该给capitals增加唯一约束,但是这样做也不会避免与cities的重复。类似,如果我们声明cities.name REFERENCES某些其它的表,这个约束不会自动广播到capitals。在这种条件下,你可以通过手工给capitals 增加同样的REFERENCES约束来做到这点。 二、分区表:

PostgreSQL教程(三):表的继承和分区表详解

1. 概述分区表: 分区的意思是把逻辑上的一个大表分割成物理上的几块儿,分区可以提供若干好处: 1). 某些类型的查询性能可以得到极大提升。 2). 更新的性能也可以得到提升,因为表的每块的索引要比在整个数据集上的索引要小。如果索引不能全部放在内存里,那么在索引上的读和写都会产生更多的磁盘访问。 3). 批量删除可以用简单地删除某个分区来实现。 4). 将很少用的数据可以移动到便宜的、慢一些地存储介质上。 假设当前的数据库并不支持分区表,而我们的应用所需处理的数据量也非常大,对于这种应用场景,我们不得不人为的将该大表按照一定的规则,手工拆分成多个小表,让每个小表包含不同区间的数据。这样一来,我们就必须在数据插入、更新、删除和查询之前,先计算本次的指令需要操作的小表。对于有些查询而言,由于查询区间可能会跨越多个小表,这样我们又不得不将多个小表的查询结果进行union操作,以合并来自多个表的数据,并最终形成一个结果集返回给客户端。可见,如果我们正在使用的数据库不支持分区表,那么在适合其应用的场景下,我们就需要做很多额外的编程工作以弥补这一缺失。然而需要说明的是,尽管功能可以勉强应付,但是性能却和分区表无法相提并论。 目前PostgreSQL支持的分区形式主要为以下两种: 1). 范围分区: 表被一个或者多个键字字段分区成"范围",在这些范围之间没有重叠的数值分布到不同的分区里。比如,我们可以为特定的商业对象根据数据范围分区,或者根据标识符范围分区。 2). 列表分区: 表是通过明确地列出每个分区里应该出现那些键字值实现的。

2. 实现分区: 1). 创建"主表",所有分区都从它继承。 2). 创建几个"子"表,每个都从主表上继承。通常,这些"子"表将不会再增加任何字段。我们将把子表称作分区,尽管它们就是普通的PostgreSQL表。 上面创建的子表,均已年、月的形式进行范围划分,不同年月的数据将归属到不同的子表内。这样的实现方式对于清空分区数据而言将极为方便和高效,即直接执行DROP TABLE语句删除相应的子表,之后在根据实际的应用考虑是否重建该子表(分区)。相比于直接DROP子表,PostgreSQL还提供了另外一种更为方便的方式来管理子表: 和直接DROP相比,该方式仅仅是使子表脱离了原有的主表,而存储在子表中的数据仍然可以得到访问,因为此时该表已经被还原成一个普通的数据表了。这样对于数据库的DBA来说,就可以在此时对该表进行必要的维护操作,如数据清理、归档等,在完成诸多例行性的操作之后,就可以考虑是直接删除该表(DROP TABLE),还是先清空该表的数据(TRUNCATE TABLE),之后再让该表重新继承主表,如: 3). 给分区表增加约束,定义每个分区允许的健值。同时需要注意的是,定义的约束要确保在不同的分区里不会有相同的键值。因此,我们需要将上面"子"表的定义修改为以下形式: 4). 尽可能基于键值创建索引。如果需要,我们也同样可以为子表中的其它字段创建索引。 5). 定义一个规则或者触发器,把对主表的修改重定向到适当的分区表。 如果数据只进入最新的分区,我们可以设置一个非常简单的规则来插入数据。我们必须每个月都重新定义这个规则,即修改重定向插入的子表名,这样它总是指向当前分区。 其中NEW是关键字,表示新数据字段的集合。这里可以通过点(.)操作符来获取集合中的每一个字段。 我们可能想插入数据并且想让服务器自动定位应该向哪个分区插入数据。我们可以用像下面这样的更复杂的规则集来实现这个目标。 请注意每个规则里面的WHERE子句正好匹配其分区的CHECK约束。 可以看出,一个复杂的分区方案可能要求相当多的DDL。在上面的例子里我们需要每个月创建一次新分区,因此写一个脚本自动生成需要的DDL是明智的。除此之外,我们还不难推断出,分区表对于新数据的批量插入操作有一定的抑制,这一点在Oracle中也同样如此。 除了上面介绍的通过Rule的方式重定向主表的数据到各个子表,我们还可以通过触发器的方式来完成此操作,相比于基于Rule的重定向方法,基于触发器的方式可能会带来更好的插入效率,特别是针对非批量插入的情况。然而对于批量插入而言,由于Rule的额外开销是基于表的,而不是基于行的,因此效果会好于触发器方式。另一个需要注意的是,copy操作将会忽略Rules,如果我们想要通过COPY方法来插入数据,你只能将数据直接copy到正确的子表,而不是主表。这种限制对于触发器来说是不会造成任何问题的。基于Rule的重定向方式还存在另外一个问题,就是当插入的数据不在任何子表的约束中时,PostgreSQL也不会报错,而是将数据直接保留在主表中。

6). 添加新分区:

这里将介绍两种添加新分区的方式,第一种方法简单且直观,我们只是创建新的子表,同时为其定义新的检查约束,如: 第二种方法的创建步骤相对繁琐,但更为灵活和实用。见以下四步: 7). 确保postgresql.conf里的配置参数constraint_exclusion是打开的。没有这个参数,查询不会按照需要进行优化。这里我们需要做的是确保该选项在配置文件中没有被注释掉。 3. 分区和约束排除: 约束排除(Constraint exclusion)是一种查询优化技巧,它改进了用上面方法定义的表分区的性能。比如: 如果没有约束排除,上面的查询会扫描measurement表中的每一个分区。打开了约束排除之后,规划器将检查每个分区的约束然后再视图证明该分区不需要被扫描,因为它不能包含任何符合WHERE子句条件的数据行。如果规划器可以证明这个,它就把该分区从查询规划里排除出去。 你可以使用EXPLAIN命令显示一个规划在constraint_exclusion打开和关闭情况下的不同。用上面方法设置的表的典型的缺省规划是: 从上面的查询计划中可以看出,PostgreSQL扫描了所有分区。下面我们再看一下打开约束排除之后的查询计划: 请注意,约束排除只由CHECK约束驱动,而不会由索引驱动。 目前版本的PostgreSQL中该配置的缺省值是partition,该值是介于on和off之间的一种行为方式,即规划器只会将约束排除应用于基于分区表的查询,而on设置则会为所有查询都进行约束排除,那么对于普通数据表而言,也将不得不承担由该机制而产生的额外开销。 约束排除在使用时有以下几点注意事项: 1). 约束排除只是在查询的WHERE子句包含约束的时候才生效。一个参数化的查询不会被优化,因为在运行时规划器不知道该参数会选择哪个分区。因此像CURRENT_DATE这样的函数必须避免。把分区键值和另外一个表的字段连接起来也不会得到优化。 2). 在CHECK约束里面要避免跨数据类型的比较,因为目前规划器会无法证明这样的条件为假。比如,下面的约束会在x是整数字段的时候可用,但是在x是一个bigint的时候不能用: CHECK (x = 1) 对于bigint字段,我们必须使用类似下面这样的约束: CHECK (x = 1::bigint) 这个问题并不仅仅局限于bigint数据类型,它可能会发生在任何约束的缺省数据类型与其比较的字段的数据类型不匹配的场合。在提交的查询里的跨数据类型的比较通常是OK的,只是不能在CHECK条件里。 3). 在主表上的UPDATE和DELETE命令并不执行约束排除。 4). 在规划器进行约束排除时,主表上的所有分区的所有约束都将会被检查,因此,大量的分区会显著增加查询规划的时间。 5). 在执行ANALYZE语句时,要为每一个分区都执行该命令,而不是仅仅对主表执行该命令。

PostgreSQL教程(二):模式Schema详解 一个数据库包含一个或多个命名的模式,模式又包含表。模式还包含其它命名的对象,包括数据类型、函数,以及操作符。同一个对象名可以在不同的

PostgreSQL教程(四):数据类型详解 一、数值类型:下面是PostgreSQL所支持的数值类型的列表和简单说明:1.整数类型:类型smallint、integer和bigint存储各种范围的全部是数字的数,也就是没

PostgreSQL教程(五):函数和操作符详解(1) 一、逻辑操作符:常用的逻辑操作符有:AND、OR和NOT。其语义与其它编程语言中的逻辑操作符完全相同。二、比较操作符:下面是PostgreSQL中提供的比较

标签: PostgreSQL教程(三):表的继承和分区表详解

本文链接地址:https://www.jiuchutong.com/biancheng/312238.html 转载请保留说明!

上一篇:PostgreSQL教程(一):数据表详解

下一篇:PostgreSQL教程(二):模式Schema详解

  • 塑料制品开票税率
  • 企业所得税中资产折旧调整明细表中提示折旧年限
  • 一次性用品可以做什么
  • 小规模纳税人发票怎么做账
  • 林业一般纳税人的税率是多少?
  • 个人劳务附加税税率表
  • 个人独资企业租赁收入如何纳税
  • 小规模纳税人减征额怎么计算
  • 自行建造固定资产中的自营工程,在领用工程物资
  • 以物抵债计税依据
  • 单位风险金是什么意思
  • 总公司调到子公司
  • etc开了充值发票还可以开消费发票么?
  • 生产用的软件
  • 2018购房契税税率
  • 以前年度进项税少记了如何调整
  • 当月凭证做完怎么结转?
  • bootmgr is missing怎么手动解决
  • 调整以前年度的收入怎么入账
  • thinkphp yii
  • php货币换算人民币
  • PHP:session_save_path()的用法_Session函数
  • 城市里创业
  • 棕榈滩的读音
  • 动销率怎么看
  • php调用其他php
  • c++stl详解
  • php实现批量删除
  • 外贸出口退税操作流程
  • 购买车辆的进项税怎么抵扣
  • 可变现净值高于成本是什么意思
  • 跨年的发票可以退税吗
  • phpcms api
  • 数据库触发器db2什么意思
  • 一般纳税人零申报报税流程
  • 进项税额有留底税额吗
  • 收外汇是一定要交税吗
  • 企业会计制度固定资产折旧年限
  • mysql将两个查询结果合并到一起
  • 工会经费可以列支哪些项目
  • 银行存款期初余额调整会计分录
  • 期末留底的进项税怎么下账
  • ubuntu打开设置
  • 净利润率的计算方法公式
  • 建筑行业工程施工当月可以不结转吗
  • 厂房监理要点
  • 出差补助没有发票
  • 哪些发票不能开专票
  • 金蝶k3怎么新增会计科目
  • 进项税留抵怎么做分录
  • 采购商品的运费会计分录
  • 未达到起征点的税金怎么做凭证
  • 管理费用一般包含研发费用吗
  • 企业支付宝要交税吗?
  • 部门财务独立核算原则有哪些
  • 为什么要依法管理
  • 比较常见的成语有哪些
  • win10创建家庭
  • win10打开或关闭
  • 如何用pe弄双系统引导
  • xp清理系统的命令
  • Windowsxp桌面没有图标怎么办
  • win7系统设置鼠标灵敏度
  • 网卡被禁用一启动就死机
  • windows更新后桌面没反应
  • win8怎样设置禁止弹出广告
  • javascriptwhile
  • cocoscreator lua
  • node.js实战
  • android自定义样式
  • android仿qq聊天
  • python的条件语句有哪些关键字
  • ecmascript6 官方文档
  • python 钉钉打卡定位
  • pyqt5编译
  • js设计模式和开发实践
  • js function的this指向
  • javascript面向对象精要pdf
  • 国家税务总局2012年20号公告
  • 2023河南新农合截止日期新规
  • 免责声明:网站部分图片文字素材来源于网络,如有侵权,请及时告知,我们会第一时间删除,谢谢! 邮箱:opceo@qq.com

    鄂ICP备2023003026号

    网站地图: 企业信息 工商信息 财税知识 网络常识 编程技术

    友情链接: 武汉网站建设