Oracle 临时表(Temporary Table)

Oracle 临时表(Temporary Table)

适用版本:Oracle Database 8i / 9i / 10g / 11g / 12c / 19c / 23ai 文档版本:v1.0 / 2026-07


1. 概述

临时表 存储会话或事务临时数据[1]:

特点

  • 数据临时
  • 结构永久
  • 自动清理
  • 不产生 redo

2. 创建

2.1 会话级

CREATE GLOBAL TEMPORARY TABLE temp_emp (
  id NUMBER,
  name VARCHAR2(100),
  salary NUMBER
) ON COMMIT PRESERVE ROWS;

2.2 事务级

CREATE GLOBAL TEMPORARY TABLE temp_emp (
  id NUMBER,
  name VARCHAR2(100),
  salary NUMBER
) ON COMMIT DELETE ROWS;

2.3 索引

CREATE INDEX idx_temp_emp_id ON temp_emp(id);

3. 数据生命周期

3.1 ON COMMIT DELETE ROWS

INSERT → COMMIT → 数据自动删除

3.2 ON COMMIT PRESERVE ROWS

INSERT → COMMIT → 数据保留
会话结束 → 数据删除

4. 特性

4.1 优势

  • 不产生 redo(仅 undo)
  • 减少日志
  • 性能好
  • 自动清理

4.2 限制

  • 不能分区
  • 不能外键约束
  • 不能 VARRAY/NESTED TABLE
  • 索引临时

5. 应用场景

5.1 中间结果

-- 复杂计算中间存储
INSERT INTO temp_result 
SELECT ... FROM big_table WHERE ...;

SELECT ... FROM temp_result;

5.2 批量处理

-- 批量数据处理
FOR batch IN cur LOOP
  DELETE FROM temp_batch;
  INSERT INTO temp_batch VALUES (...);
  
  -- 处理
  ...
END LOOP;

5.3 跨 SQL 共享

-- 多 SQL 共享临时数据
INSERT INTO temp_data SELECT ... FROM ...;

-- 多次查询
SELECT * FROM temp_data WHERE ...;
SELECT * FROM temp_data WHERE ...;
SELECT * FROM temp_data WHERE ...;

5.4 报表

-- 报表中间数据
INSERT INTO temp_report 
SELECT ... FROM sales WHERE sale_date BETWEEN ...;

SELECT * FROM temp_report;

6. 私有临时表(18c+)

6.1 创建

CREATE PRIVATE TEMPORARY TABLE ora$ptt_temp_emp AS
SELECT * FROM employees WHERE 1=0;

6.2 特点

  • 内存中
  • 会话或事务级
  • 命名必须以 ORA$PTT_ 开头
  • 更快

7. 常见坑与排错

7.1 数据消失

-- ON COMMIT DELETE ROWS:COMMIT 后数据消失
-- 检查 ON COMMIT 选项

7.2 TRUNCATE 临时表

-- TRUNCATE 仅清当前会话数据
TRUNCATE TABLE temp_emp;

7.3 统计信息

-- 临时表统计信息
EXEC DBMS_STATS.GATHER_TABLE_STATS('SCOTT', 'TEMP_EMP');

8. 最佳实践

  1. 会话级用 PRESERVE:跨 SQL 共享
  2. 事务级用 DELETE:自动清理
  3. 加索引提升性能:临时索引
  4. 避免大数据量:内存压力
  5. 定期 TRUNCATE:释放空间
  6. 私有临时表 18c+:内存快

9. 参考资料

[1] Oracle Database SQL Language Reference 19c, “CREATE TABLE” https://docs.oracle.com/en/database/oracle/oracle-database/19/sqlrf/CREATE-TABLE.html