Oracle 逻辑结构篇 之逻辑结构(三)段和区
mhr18 2024-09-20 20:55 20 浏览 0 评论
三、段
在数据库中包含了,每个表空间物理上对应着磁盘上的一个或多个数据文件DATAFILE),一个数据文件只能属于一个表空间。每个表空间又有多个段(SEGMENT组成。
(一)、段类型
当建立数据对象(表、索引、簇等)时,Oracle 会自动给这些数据对象分配相应的存储空间,以存放它们的数据信息,这些为数据对象所分配的存储空间被称为段。一个段只能存放在一个表空间上,但是可分布在属于这个表空间中的多个数据文件中。段是由一个或多个区组成的,段的大小是该段所有区大小总和。在 Oracle 数据库中,每个段只属于一个特定的数据库对象(表、索引等),在这个段中至少包含一个区(初始区)。每种数据对象都具有相应的段,Oracle 提供了以下一些段类型:
1)表段(Table):
表是在数据库内存储数据的最常用方法。表段用于存储常规表(非集簇且未分区)的的数据。表段中的所有数据都必须存储在一个表空间内。例如,当在 USERS_DATA 表空上建立表 S_EMP 时,Oracle 会建立名称为 S_EMP 的表段,并且将该表的所有数据存放在USERS_DATA 表空间上。如果表中有 LOB 列或 VARRAY 列,那么该表不会将这些数据列存储在同一个段。
2)表分区段(Table Partition):
表分区主要用于数据仓库应用。当表中包含大量数据且表的并发使用率很高时,可以把一张大表数据划分成几个小的分区,其中每个分区对应于一个段,这种段类型被称为表分段,并且每个表分区段可以存放到不同表空间上。使用表分区可以降低 I/O 次数,提高 /O 性能。表分区后,每个分区都是一个段,可以指定存储参数单独对它们进行控制。假定一张销售表年数据总量达到 10GB,每个季度平均 2.5GB,如果使用普通表存储数据,那么0GB 数据会存放到一个表段中,那么在统计一季度销售数据时需要扫描 10GB 数据;而如果使用表分区段,那么可以将一、二、三、四季度数据分别存放到不同表分区段中,此时统计一季度销售数据只需要扫描 2.5GB 数据。显然,使用表分区段可以大大降低 I/O 次数并提高 I/O 性能。
注意:使用这种类型的段需要在 Oracle9i 企业版内选择分区(Partitioning) 组件
3)簇段(Cluster):
簇与表一样,是一种数据段类型。簇内的行是基于键值存储的,一个簇可以包含一个或多个表,一个簇内所有的表属于同一个段,并且区和块的存储管理方式也完全相同。例如,如果经常要执行主从表之间的连接查询,那么可以将这两张表的数据组织到簇中。簇段的名称与簇名完全相同。注意,当将表放到簇中时,表的数据存放在簇段中,而不会为该表建立专门的表段。假定在 USERS 表空间上建立簇 ORD_ITEM_CLU,并且将表 ORD 和 ITEM 组织到该簇中,此时只会建立簇段 ORD_ITEM_CLU,而不会建立表段 ORD 和 ITEM。
4)索引段(Index):
索引是用于加快查询速度的数据库对象。当建立索引时,Oracle 会为该索引建立相应的索引段,索引段的名称与索引名完全相同,并且一个索引段只能存放在一个表空间中。如果一个表有三个索引,则使用三个索引段。使用索引段的目的是根据指定的关键字来查找行在表内的位置。例如,当在 EMP 表的 EMPNO 列上建立索引 PK_EMP 时,Oracle 会自动建立索引段 PK_EMP。
5)按索引组织的表段(Index-organized table):
一般情况下,表与索引数据分别存放在表段和索引段中。例如,表 EMP 及其索引PK_EMP 的数据分别存放在表段 EMP 和索引段 PK_EMP 中。但是,如果经常要通过主键列检索数据,那么 Oracle 建议将这种表建立为索引组织表。当建立索引组织表时,表和其主键索引的数据会存放到同一个段中,该段被称为索引组织表段。在按索引组织的表内,数据基于主键键值存储在索引内。按索引组织的表无需在表中进行查找,因为所有数据都可以直接从索引树中检索到。
6)索引分区段(Index Partition):
索引分区类似于表分区,而且只能在分区表上建立索引分区。通过对索引进行分区,可以将一个大的索引划分成几个小的分区,并且每个分区对应一个段,这种段被称为索引分区段。分区索引的主要用途在于,通过分散索引输入/输出(I/O) 来最大限度地降低对系统资源的争用。使用这种类型的段需要在 Oracle9i 企业版内选择分区(Partitioning) 组件。
7)还原段(Undo):
还原段由正在对数据库进行更改的事务处理使用,还原段用于存放事务所修改数据的旧值。在修改表或索引数据时,Oracle 会将修改前的数据存放到还原段中,以使得用户可以取消错误操作。例如,当执行"UPDATE emp SET sal=1000 WHERE empno=7788"语句时,假定雇员 7788 原有工资为 800,那么 800 将会存放到还原段中,而新数据 1000 将会存放到EMP 段中。
8)临时段(Temporary Segment):
当用户执行 CREATE INDEX、SELECT DISTINCT 和 SELECT GROUP BY 等命令时,Oracle 服务器就会在内存中(排序区中,大小由初始化参数 SORT_AREA_SIZE 确定)执行排序。如果排序所需空间大于内存中的可用空间,则将中间结果写入到磁盘上。临时段用来存储这些中间结果。假定某表的数据为 7788,7235,8769,2020,8986,那当使用 ORDER BY 子句进行排序时,会返回数据 2020,7235,7788,8769,8986。这些返回的数据被称为临时数据,这些数据存放到临时段中。
当执行以下操作时会产生临时数据:
- ? CREATE INDEX
- ? SELECT...ORDERBY
- ? SELECT DISTINCT...
- ? SELECT...GROUPBY
- ? SELECT...UNION
- ? SELECT...INTERSECT
- ? SELECT...MINUS
- ? ANALYZE 命令
9)LOB 段:
当表中的数据包含文本文档、图像或者视频时,使用普通数据类型如 VARCHAR 等可能无法存储,必须使用 CLOB 或 BLOB 数据类型存储大型对象(LOB)。如果 LOB 列数据长度大于 4000B,Oracle 服务器将把这些值存储在独立的段(称为“LOB 段”)中。而在基表(Base Table)中只包含一个定位器或者指针,指向对应的 LOB 数据所在的位置除了上述 9 种段类型外,还有 LOB 索引段,嵌套表段,引导程序段(也称为高速缓存段)等多种段类型,在此不做介绍。
【实例3-1】查询 scott 用户拥有的段类型和个数。
1)以 sys 用户登录 CONN / AS SYSDBA已连接 2) 查询 SQL> SELECT SEGMENT_TYPE,COUNT(*) SEG_COUNTFROM dba_segmentsWHERE owner='SCOTT'GROUP BY SEGMENT_TYPE; SEGMENT_TYPE SEG_COUNT ------------------ ---------- INDEX 3TABLE 9;
SCOTT 模式有 3 个索引段和 9 个数据段。
(二)、存储从句的优先关系
在创建段时,可以为它指定 pctfree、pctused 等参数,来控制其中块存储空间管理方式,也可以为它指定 initial、next、pctincrease 等存储参数,以指定其中区的分配方式。这些参数设置可以是数据库级别的,即使用数据库默认的区分配和管理方式,也可以在表空间级别的,即通过 EXTENT MANAGEMENT 子句及 DEFAULT STORAGE 子句指定区的分配和管理方式,也可以在段级别,即指定存储子句(DEFAULT STORAGE 子句),以控制如何向段分配区。那么存储子句的优先关系如何呢,Oracle 服务器按以下的方式进行区的管理(如图 P1-1所示):
- ? 除了 MINIMUM EXTENT 和 UNIFORM SIZE 表空间参数外,在段级别指定的任何存储参数优先级最高,覆盖在表空间级别设置的相应选项。
- ? 如果没有在段级别明确设置存储参数,那么存储参数缺省值为在表空间级别所设置的值。
- ? 如果没有在表空间级别明确设置存储参数,那么将使用 Oracle 服务器系统的缺省设置。
还要注意,某些参数无法在表空间级别指定,而只能在段级别指定。如果存储参数改变,参数的改变只影响新分配区,而对已分配的区不产生影响。如果指定了表空间的最小区大小,分配给该表空间内的段的最小区个数是固定的。
四、区的分配和撤销
数据扩展(extent)是由一组连续的数据块(data block)构成的数据库逻辑存储分配单位。而段(segment)则是由一个或多个数据扩展构成。当一个段中已有空间已经用完,Oracle为这个段分配新的数据扩展。
(一)、数据扩展何时被分配
当用户创建数据表时,Oracle 为此表的数据段(data segment)分配一个包含若干数据块(data block)的初始数据扩展(initial extent)。虽然此时数据表中还没有数据,但是此初始数据扩展中的数据块已经为插入新数据做好了准备。
如果一个段(segment)的初始数据扩展(initial extent)中的数据块(data block)都已装满,且有新数据插入需要空间时,Oracle 自动为这个段分配一个增量数据扩展(incrementalextent)。增量数据扩展是一个段中继已有数据扩展之后分配的后续数据扩展,她的容量大于或等于之前的数据扩展。
为了管理的需要,每个段(segment)的段头(header block)中包含一个记录此段所有数据扩展(extent)的目录。
(二)、如何决定数据扩展分配时的数量与容量
每个段(segment)的定义中都包含了数据扩展(extent)的存储参数(storage parameter)存储参数适用于各种类型的段。这个参数控制着 Oracle 如何为段分配可用空间。例如,用户可以在 CREATE TABLE 语句中使用 STORAGE 子句设定存储参数,决定创建表时为其数据段(data segment)分配多少初始空间,或限定一个表最多可以包含多少数据扩展。如果用户没有为表设定存储参数,那么表在创建时使用所在表空间(tablespace)的默认存储参数。
用户既可以使用数据字典管理的表空间(dictionary managed tablespace)(依赖数据字典表监控空间的利用情况),也可以使用本地管理的表空间(locally managed tablespace)(使用位图(bitmap)来标记可用与已用空间)。由于本地管理的表空间性能较好且易于管理,当用户没有显式地设定数据扩展(extent)管理参数时,除了 SYSTEM 之外的所有永久表空间(permanent tablespace)默认使用本地管理方式。
在一个本地管理的表空间中,其中所分配的数据扩展(extent)的容量既可以是用户设定的固定值,也可以是由系统自动决定的可变值。当用户创建表空间(tablespace)时可以使用 UNIFORM (用户指定)或 AUTOALLOCATE (由系统管理)子句设定数据扩展的分配方式。对于固定容量(UNIFORM)的数据扩展,用户可以为数据扩展设定容量或使用默认大小(1 MB)。用户须确保每个数据扩展的容量至少能包含 5 个数据块(database block)。本地管理(locally managed)的临时表空间(temporary tablespace)在分配数据扩展时只能使用此种方式。
对于由系统管理(AUTOALLOCATE)的数据扩展,由 Oracle 决定新增数据扩展的最佳容量,其最小容量为 64 KB。如果创建表空间时使用了“segment space management auto”子句,且数据块容量大于等于 16 KB,Oracle 扩展一个段时(segment)所创建的数据扩展的最小容量为 1 MB。对于永久表空间(permanent tablespace)上述参数均为默认值。
在本地管理的表空间(locally managed tablespace)中,INITIAL,NEXT,PCTINCREASE, 和 MINEXTENTS 这四个存储参数可以作用于段(segment),但不能作用于表空间。INITIAL,NEXT,PCTINCREASE,和 MINEXTENTS 相结合可以用于计算段的初始容量。当段容量确定后,Oracle 使用内部算法确定其中每个初始数据扩展(extent)的容量。
(三)、数据扩展如何被分配
依据表空间管理方式的不同(本地管理(locally managed)或数据字典管理(dictionarymanaged)),选择不同的算法分配数据扩展(extent)。
对于本地管理的表空间(locally managed tablespace),Oracle 在为新的数据扩展(extent)寻找可用空间时,首先选择一个属于此表空间的数据文件(datafile),再搜索此数据文件的位图(bitmap)查找连续的数据块(free block)。如果此数据块中没有足够的连续可用空间Oracle 将查询其他数据文件。
举例说明,当创建表段时,Oracle 将为段分配一个“初始区”(Initial Extent),时,由于表不存在任何数据,初始区中的每个块每是未使用的。随着不断向表插入数据,始区的块不断写满,当初始区中的块都被写满后,数据段会向 Oracle 申请新的存储空间,这时 Oracle 为表段再分配一个“后继区”,后继区写满后再分配新区。这些区被标记为“已用区”通常分配给段的区将一直保留在段中,不论区中是否存有数据.当删除数据库对象时,组成对象段的所有区全部回收,即变为“空闲区”。
写在最后的话
感谢各位的支持与阅读,后续会继续推送相关知识和交流,欢迎交流、转发和关注,感谢!
相关推荐
- 一文带您了解数据库的行列之争:行式与列式存储的异同
-
数据库存储格式是数据库管理系统中一个至关重要的方面,它直接影响到数据的组织和检索效率。在数据库中,有两种主要的存储格式,即行式存储和列式存储。这两者采用截然不同的方法来组织和存储数据,各自具有一系列优...
- NL2SQL(三)开源项目怎么选:talk is cheap, show me the code!
-
老规矩,先看效果下面的demo来自试用的SuperSonic,将会在下面详细介绍:大模型时代Text-to-SQL特点随着基于LLM技术的发展,RAG/AIAgent/Fine...
- JDK25长期支持版九月降临:18项王炸功能全解析
-
Java要放大招啦!9月份推出的JDK25长期支持版已经锁定18个超能力,从稳定值到结构化并发,还有Linux系统下的"预知未来"性能分析!下面我用打游戏的术语给你们掰扯明白:1、飞...
- OceanBase 推出单机版 高度兼容MySQL和Oracle
-
【环球网科技综合报道】3月27日,独立数据库厂商OceanBase正式发布单机版产品。据悉,这一产品基于自主研发的单机分布式一体化架构设计,具备极简数据库架构和高度兼容性,为中小规模业务提供兼具性能与...
- 黄远邦:应对7月1日闰秒对Oracle数据库影响
-
由于今年7月1日全世界会多出一秒,这可能对时间敏感的IT系统造成较大影响。中亦科技数据库团队对此问题做了深入的研究,并对用户系统提出了相应的解决方法及建议。中亦科技数据库产品总监黄远邦认为,闰秒调整会...
- MySQL数据库密码忘记了,怎么办?(mysql 数据库密码)
-
#头条创作挑战赛#MySQL数据库密码忘记了且没有其他可以修改账号密码的账户时怎么办呢?登录MySQL,密码输入错误/*密码错误,报如下错误*/[root@TESTDB~]#mysql-u...
- Chinese AI Talent in Spotlight as Nvidia and Meta Escalate Talent War
-
OntherightisBanghuaZhu,ChiefResearchScientistatNVIDIATMTPOST--SiliconValley’stoptech...
- 用Cursor开启JAVA+AI生涯(javascirpt怎么开启)
-
Cursor是基于VSCode开发的一款编辑器,支持多种语言的开发编辑。与传统的开发工具相比,它有多种优势:与AI无缝集成,响应速度快,占用内存小。但很多同学在"起步"过程中遇到了...
- 毕业十年了,自从做了开发用了很多软件,但距离写开发工具还很远
-
办公系统类:办公软件Word、Excel、PowerPoint三大必备技能+腾讯/金山在线文档解压缩操作:7-zip/winrar文件文本处理:Notepad++(文本编辑器正则表达式超级好...
- 盘点Java中最没用的知识⑤:这3个老古董你还在代码里“考古”?
-
一、Stack类:“继承Vector”的历史bug,为何成了性能拖油瓶?你是不是在学Java集合时,老师说过“栈结构用Stack类”?是不是在老代码里见过"newStack<>(...
- Gemini 2.5 Pro 0506发布,编程最强大模型, 碾压 Claude3.7 sonnent
-
一、Gemini2.5Pro(I/Oedition)发布1、为何叫I/Oedition?谷歌史上最强编程模型Gemini2.5Pro(I/Oedition)发布,具体型号是Gemin...
- 如何让无聊变得有趣(附本人大量美图)
-
文/图:金冬成在这条长300公里的公路上,我已经来回往返了无数次。3小时车程,一个人,想想都是多么无聊的一件事。其实,人生道路上,类似这种无聊的事情有很多很多。无聊的事情、枯燥的工作,往往让我们容易失...
- Oracle 推出 Java 24,增强 AI 支持和后量子加密
-
导读:Oracle宣布正式发布Java24,该语言增加了几个新功能,例如StreamGatherersAPI和Class-FileAPI的可用性,以及专门为AI推理和量子安全设计...
- 公司ERP突然变慢?“索引重建”这颗“药”可不能随便吃!
-
各位老板、IT小哥、财务小姐姐,有没有遇到过公司ERP系统突然卡顿得像“老爷车”,点个按钮半天没反应,急得直跺脚?这时候,可能有人会跳出来说:“我知道,重建一下数据库索引就好了!”听起来像个“神操作”...
- 基于Java实现,支持在线发布API接口读取数据库,有哪些工具?
-
基于java实现,不需要编辑就能发布api接口的,有哪些工具、平台?还能一键发布、快速授权和开放提供给第三方请求调用接口的解决方案。架构方案设计:以下是一些基于Java实现的无需编辑或只需少量编辑...
你 发表评论:
欢迎- 一周热门
- 最近发表
-
- 一文带您了解数据库的行列之争:行式与列式存储的异同
- NL2SQL(三)开源项目怎么选:talk is cheap, show me the code!
- JDK25长期支持版九月降临:18项王炸功能全解析
- OceanBase 推出单机版 高度兼容MySQL和Oracle
- 黄远邦:应对7月1日闰秒对Oracle数据库影响
- MySQL数据库密码忘记了,怎么办?(mysql 数据库密码)
- Chinese AI Talent in Spotlight as Nvidia and Meta Escalate Talent War
- 用Cursor开启JAVA+AI生涯(javascirpt怎么开启)
- 毕业十年了,自从做了开发用了很多软件,但距离写开发工具还很远
- 盘点Java中最没用的知识⑤:这3个老古董你还在代码里“考古”?
- 标签列表
-
- oracle位图索引 (74)
- oracle批量插入数据 (65)
- oracle事务隔离级别 (59)
- oracle 空为0 (51)
- oracle主从同步 (55)
- oracle 乐观锁 (51)
- redis 命令 (78)
- php redis (88)
- redis 存储 (66)
- redis 锁 (69)
- 启动 redis (66)
- redis 时间 (56)
- redis 删除 (67)
- redis内存 (57)
- redis并发 (52)
- redis 主从 (69)
- redis 订阅 (51)
- redis 登录 (54)
- redis 面试 (58)
- 阿里 redis (59)
- redis 搭建 (53)
- redis的缓存 (55)
- lua redis (58)
- redis 连接池 (61)
- redis 限流 (51)