用exchange partition和split partition将表分区。

本文是以下面文章为基础做练习测试:

http://www.oracle-base.com/articles/misc/partitioning-an-existing-table-using-exchange-partition.php

这个方法更适合在生产环境中将普通表变为分区表。

主要方法有分区转换与分区分裂。

.创建一个模拟环境

1. 创建一个小表

SQL> create table lookup(

id number(10),

description varchar2(50)

 );

加主键

SQL> alter table lookup add ( constraint lookup_pk primary key(id));

插入数据

SQL> INSERT INTO lookup (id, description) VALUES (1, 'ONE');

INSERT INTO lookup (id, description) VALUES (2, 'TWO');

INSERT INTO lookup (id, description) VALUES (3, 'THREE');

 

2.创建一个大表

SQL> CREATE TABLE big_table (

id  NUMBER(10),

created_date  DATE,

lookup_id  NUMBER(10),

data  VARCHAR2(50)

);

增加数据:

 

SQL> declare
t_lookup_id lookup.id%TYPE;
t_create_date date;
begin
for i in 1 .. 1000000 loop
if mod(i,3)=0 then
t_create_date:=add_months(sysdate,-24);
t_lookup_id :=2;
elsif mod(i,2)=0 then
t_create_date:=add_months(sysdate,-12);
t_lookup_id :=1;
else
t_create_date:=sysdate;
t_lookup_id:=3;
end if;
INSERT INTO big_table(id, created_date, lookup_id, data) VALUES (i, t_create_date, t_lookup_id, 'This is some data for ' || i);
end loop;
commit;
end;
/ 

加主键

ALTER TABLE big_table ADD (

  CONSTRAINT big_table_pk PRIMARY KEY (id)

);

加外键

ALTER TABLE big_table ADD (

  CONSTRAINT bita_look_fk

  FOREIGN KEY (lookup_id)

  REFERENCES lookup(id)

);

加索引

CREATE INDEX bita_created_date_i ON big_table(created_date);

CREATE INDEX bita_look_fk_i ON big_table(lookup_id);

 

收集表信息

EXEC DBMS_STATS.gather_table_stats(USER, 'LOOKUP', cascade => TRUE);

EXEC DBMS_STATS.gather_table_stats(USER, 'BIG_TABLE', cascade => TRUE);

.创建一个分区的目标表。

SQL> create table big_table2 (

  2  id number(10),

  3  created_date date,

  4  lookup_id number(10),

  5  data varchar2(50)

  6  )

  7  partition by range (created_date)

  8  (partition big_table_2013 values less than (maxvalue));

增加主键:

SQL> alter table big_table2 add (

  2  constraint big_table_pk2 primary key(id)

  3  );

增加相应的索引

SQL> create index bita_created_date_i2 on big_table2(created_date) local;

SQL> create index bita_look_fk_i2 on big_table2(lookup_id) local;

 

增加外键

SQL>

  1  alter table big_table2 add(

  2  constraint bita_look_fk2

  3  foreign key(lookup_id)

  4* references lookup(id))

SQL> /

.分区交换(EXCHANGE PARTITION

SQL> alter table big_table2

  2  exchange partition big_table_2013

  3  with table big_table

  4  without validation

  5  update global indexes;

SQL> drop table big_table;

SQL> rename big_table2 to big_table;

SQL> alter table big_table rename constraint big_table_pk2 to big_table_pk;

SQL> alter table big_table rename constraint bita_look_fk2 to bita_look_fk;

SQL> alter index big_table_pk2 rename to big_table_pk;

SQL> alter index bita_look_fk_i2 rename to bita_look_fk_i;

SQL> alter index bita_created_date_i2 rename to bita_created_date_i;

.分区分裂(SPLIT PARTITION

SQL> alter table big_table

  2  split partition big_table_2013 at(to_date('31-dec-2010 23:59:59','DD-MON-YYYY HH24:MI:SS'))

  3  into (partition big_table_2010,

  4  partition big_table_2013)

  5  update global indexes;

 

SQL> alter table big_table

  2  split partition big_table_2010 at(to_date('31-dec-2008 23:59:59','DD-MON-YYYY HH24:MI:SS'))

  3  into (partition big_table_2008,

  4  partition big_table_2010)

  5  update global indexes;

SQL> alter table big_table

  2  split partition big_table_2013 at(to_date('31-dec-2012 23:59:59','DD-MON-YYYY HH24:MI:SS'))

into (partition big_table_2012,

partition big_table_2013)

 update global indexes; 

 

SQL> exec dbms_stats.gather_table_stats(user,'big_table',cascade=>true);

.进行检查:

SQL> select partitioned from user_tables

  2  where table_name='BIG_TABLE';

 

PAR

---

YES

SQL> select partition_name,num_rows from user_tab_partitions

where table_name='BIG_TABLE';  2 

 

PARTITION_NAME                   NUM_ROWS

------------------------------ ----------

BIG_TABLE_2008                          0

BIG_TABLE_2010                          0

BIG_TABLE_2012                     666667

BIG_TABLE_2013                     333333

 

<think>嗯,用户想了解ALTER TABLE SPLIT PARTITION ... VALUES的用法说明。首先,我需要回忆一下Oracle数据库中分区表的相关操作。记得SPLIT PARTITION是用来将一个现有的分区拆分成两个部分,通常用于优化数据管理或维护。 用户可能是在处理数据增长导致的分区过大问题,或者需要重新划分数据范围。需要解释清楚这个命令的基本语法结构,比如ALTER TABLE table_name SPLIT PARTITION partition_name AT (value_list) INTO (...)。这里要强调VALUES后面的值是如何决定新分区的边界的。 接下来,要说明每个参数的作用,比如原分区名、分割点的值,以及新分区的名称存储属性。需要注意ATVALUES的区别,可能用户会混淆这两个关键字在不同数据库系统中的使用,比如在Oracle中通常用AT,而VALUES可能在其他系统中有不同用法,但需要确认是否正确。 还要提到SPLIT PARTITION的使用场景,比如数据归档、性能优化、维护等,并举一个具体的例子,比如按年份拆分分区,这样用户能更好地理解实际应用。同时,需要注意的注意事项也很重要,比如操作期间会锁表,可能影响性能,备份测试的必要性,以及索引的处理。 可能需要检查是否有其他数据库系统也支持类似的语法,比如PostgreSQL或者MySQL,但根据问题中的语法结构,更可能是Oracle。要确保语法示例正确,符合Oracle的规范,比如使用AT而不是VALUES,或者是否存在不同的版本差异。 另外,用户可能有潜在的需求,比如如何选择分割点,或者拆分后的索引状态,是否需要重建本地索引等。这些点需要在注意事项中提及,帮助用户避免常见错误。 最后,总结用法,强调正确的步骤最佳实践,确保用户在实际操作时能够安全有效地使用该命令。</think>### `ALTER TABLE SPLIT PARTITION ... VALUES` 用法详解 #### 1. **基本功能** `ALTER TABLE SPLIT PARTITION` 是 Oracle 数据库中用于 **拆分已有分区** 的 DDL 语句。其核心作用是将一个分区按照指定规则分割成两个新分区,常用于优化数据存储、平衡 I/O 负载或适应数据增长。 --- #### 2. **语法结构** ```sql ALTER TABLE 表名 SPLIT PARTITION 原分区名 AT (分割点值) INTO ( PARTITION 新分区1名 [存储属性], PARTITION 新分区2名 [存储属性] ); ``` --- #### 3. **参数说明** - **原分区名**:需要被拆分的现有分区名称。 - **AT (分割点值)**:定义分区拆分的临界值(适用于范围分区)。新分区1包含 `< 分割点值` 的数据,新分区2包含 `>= 分割点值` 的数据。 - **INTO**:指定拆分后的两个新分区的名称存储属性(如 TABLESPACE)。 --- #### 4. **使用场景** - **数据归档**:将历史数据拆分到独立分区。 - **性能优化**:缩小分区体积,提升查询效率。 - **动态扩展**:适应时间序列数据(如按年/月拆分)。 --- #### 5. **示例演示** 假设存在按年份分区的表 `sales`,需将 `p2023` 拆分为 `p2023_h1`(上半年) `p2023_h2`(下半年): ```sql ALTER TABLE sales SPLIT PARTITION p2023 AT (TO_DATE('2023-07-01', 'YYYY-MM-DD')) INTO ( PARTITION p2023_h1 TABLESPACE ts1, PARTITION p2023_h2 TABLESPACE ts2 ); ``` - **结果**: - `p2023_h1` 存储 `2023-01-01` 至 `2023-06-30` 的数据。 - `p2023_h2` 存储 `2023-07-01` 及以后的数据。 --- #### 6. **注意事项** 1. **锁表风险**:拆分操作会锁定分区,需在低峰期执行。 2. **索引维护**:全局索引需重建(`UPDATE GLOBAL INDEXES` 可避免失效)。 3. **备份建议**:操作前备份数据,避免意外丢失。 4. **兼容性**:仅适用于范围分区(LIST 分区需用 `VALUES IN` 语法)。 --- #### 7. **延伸对比** - **合并分区**:使用 `ALTER TABLE MERGE PARTITION`。 - **交换分区**:使用 `ALTER TABLE EXCHANGE PARTITION` 快速迁移数据。 通过合理使用分区操作,可显著提升大表管理效率 ✅。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值