如何通过查询DBA_OBJECTS表的CREATED字段来获取Oracle数据库中各段的创建时间?

2026-05-03 07:011阅读0评论SEO资讯
  • 内容介绍
  • 文章标签
  • 相关推荐

本文共计807个文字,预计阅读时间需要4分钟。

如何通过查询DBA_OBJECTS表的CREATED字段来获取Oracle数据库中各段的创建时间?

相关专题:

oracle 中段(segment)的创建时间,本质上就是其对应数据库对象(如表、索引、lob等)的创建时间,直接查 dba_objectscreated 字段即可——但必须注意:这不是段物理分配时间,而是对象首次 ddl 成功执行的时间,且该字段不会随 truncatemove 或高水位调整而更新。

为什么不能直接查 DBA_SEGMENTS 的 CREATED 字段

DBA_SEGMENTS 视图里根本没有 CREATED 列。它只提供段的物理属性(如 BYTESEXTENTSSEGMENT_NAMESEGMENT_TYPE),不记录元数据时间戳。试图 SELECT CREATED FROM DBA_SEGMENTS 会报 ORA-00904: "CREATED": invalid identifier 错误。

DBA_OBJECTS.CREATED 是最可靠来源

只要对象属于段类型(SEGMENT_TYPE IN ('TABLE', 'INDEX', 'LOBSEGMENT', 'LOBINDEX', 'TABLE PARTITION', 'INDEX PARTITION' 等),它的 CREATED 值就代表该段首次被创建的时间点。使用时需注意:

  • DBA_OBJECTS 要求 SELECT_CATALOG_ROLEDBA 权限,普通开发用户通常无权访问
  • OBJECT_NAMEOWNER 都是大写存储,建议显式用 UPPER() 或全大写匹配,避免大小写问题
  • CREATEDDATE 类型,精度到秒,不包含毫秒或时区信息
  • 如果对象被 DROP 后重建,CREATED 会变成新时间;但如果是 ALTER ... MOVEREBUILDCREATED 不变,只有 LAST_DDL_TIME 更新

关联 DBA_SEGMENTS 获取段级物理信息

要同时拿到段大小和创建时间,得把 DBA_SEGMENTSDBA_OBJECTS 关联查询。关键匹配字段是 OWNER + SEGMENT_NAME = OWNER + OBJECT_NAME,且限定 OBJECT_TYPESEGMENT_TYPE 语义一致:

SELECT s.OWNER, s.SEGMENT_NAME, s.SEGMENT_TYPE, s.BYTES / 1024 / 1024 AS MB, o.CREATED FROM DBA_SEGMENTS s JOIN DBA_OBJECTS o ON s.OWNER = o.OWNER AND s.SEGMENT_NAME = o.OBJECT_NAME AND s.SEGMENT_TYPE = o.OBJECT_TYPE WHERE s.OWNER = 'SCOTT' AND s.SEGMENT_TYPE IN ('TABLE', 'INDEX', 'LOBSEGMENT');

注意:DBA_SEGMENTS 中可能有同名但不同类型的段(比如表和它的 LOB 段),所以必须用 SEGMENT_TYPE = OBJECT_TYPE 过滤,否则会多出重复或错配行。

容易忽略的权限与空值陷阱

即使你有 DBA 角色,某些对象(如全局临时表、物化视图日志)在 DBA_OBJECTS 中的 CREATED 可能为 NULL;另外,分区对象的子分区不会单独出现在 DBA_OBJECTS,只显示一级分区或模板定义。真正难搞的是:如果表建在本地管理的表空间中且启用了延迟段创建(DEFERRED_SEGMENT_CREATION=TRUE),那么刚 CREATE TABLE 后,DBA_SEGMENTS 里还没记录,但 DBA_OBJECTS 里已有 CREATED ——这时“段创建时间”实际晚于对象创建时间,直到第一次 INSERT 或手动 ALLOCATE EXTENT 才真正落地。

标签:Oracle

本文共计807个文字,预计阅读时间需要4分钟。

如何通过查询DBA_OBJECTS表的CREATED字段来获取Oracle数据库中各段的创建时间?

相关专题:

oracle 中段(segment)的创建时间,本质上就是其对应数据库对象(如表、索引、lob等)的创建时间,直接查 dba_objectscreated 字段即可——但必须注意:这不是段物理分配时间,而是对象首次 ddl 成功执行的时间,且该字段不会随 truncatemove 或高水位调整而更新。

为什么不能直接查 DBA_SEGMENTS 的 CREATED 字段

DBA_SEGMENTS 视图里根本没有 CREATED 列。它只提供段的物理属性(如 BYTESEXTENTSSEGMENT_NAMESEGMENT_TYPE),不记录元数据时间戳。试图 SELECT CREATED FROM DBA_SEGMENTS 会报 ORA-00904: "CREATED": invalid identifier 错误。

DBA_OBJECTS.CREATED 是最可靠来源

只要对象属于段类型(SEGMENT_TYPE IN ('TABLE', 'INDEX', 'LOBSEGMENT', 'LOBINDEX', 'TABLE PARTITION', 'INDEX PARTITION' 等),它的 CREATED 值就代表该段首次被创建的时间点。使用时需注意:

  • DBA_OBJECTS 要求 SELECT_CATALOG_ROLEDBA 权限,普通开发用户通常无权访问
  • OBJECT_NAMEOWNER 都是大写存储,建议显式用 UPPER() 或全大写匹配,避免大小写问题
  • CREATEDDATE 类型,精度到秒,不包含毫秒或时区信息
  • 如果对象被 DROP 后重建,CREATED 会变成新时间;但如果是 ALTER ... MOVEREBUILDCREATED 不变,只有 LAST_DDL_TIME 更新

关联 DBA_SEGMENTS 获取段级物理信息

要同时拿到段大小和创建时间,得把 DBA_SEGMENTSDBA_OBJECTS 关联查询。关键匹配字段是 OWNER + SEGMENT_NAME = OWNER + OBJECT_NAME,且限定 OBJECT_TYPESEGMENT_TYPE 语义一致:

SELECT s.OWNER, s.SEGMENT_NAME, s.SEGMENT_TYPE, s.BYTES / 1024 / 1024 AS MB, o.CREATED FROM DBA_SEGMENTS s JOIN DBA_OBJECTS o ON s.OWNER = o.OWNER AND s.SEGMENT_NAME = o.OBJECT_NAME AND s.SEGMENT_TYPE = o.OBJECT_TYPE WHERE s.OWNER = 'SCOTT' AND s.SEGMENT_TYPE IN ('TABLE', 'INDEX', 'LOBSEGMENT');

注意:DBA_SEGMENTS 中可能有同名但不同类型的段(比如表和它的 LOB 段),所以必须用 SEGMENT_TYPE = OBJECT_TYPE 过滤,否则会多出重复或错配行。

容易忽略的权限与空值陷阱

即使你有 DBA 角色,某些对象(如全局临时表、物化视图日志)在 DBA_OBJECTS 中的 CREATED 可能为 NULL;另外,分区对象的子分区不会单独出现在 DBA_OBJECTS,只显示一级分区或模板定义。真正难搞的是:如果表建在本地管理的表空间中且启用了延迟段创建(DEFERRED_SEGMENT_CREATION=TRUE),那么刚 CREATE TABLE 后,DBA_SEGMENTS 里还没记录,但 DBA_OBJECTS 里已有 CREATED ——这时“段创建时间”实际晚于对象创建时间,直到第一次 INSERT 或手动 ALLOCATE EXTENT 才真正落地。

标签:Oracle