
# 创建分区表
#### 规格约束：
单个表的最大分区数为1048575（包括一级分区和二级分区）。较多的分区会导致系统中文件数增加、占用更多的系统缓存和锁资源，进而影响系统的性能。在默认配置下，建议单个表的分区数不超过400。如果实际使用的热点分区数超过400，考虑到分区表的使用性能，建议调整FASTPATH_PART的值（调整方法参见GUC参数num_internal_lock_partitions），调整配置后，建议单个表的分区数不超过2000。
#### 创建普通分区表（创建一级分区表）
SQL语言具备强大且灵活多样的功能，其语法树往往较为复杂，分区表同样如此，分区表的创建可以理解成在原有非分区表的基础上新增表分区属性，因此分区表的语法接口可以看成是对原有非分区表CREATE TABLE语句进行扩展PARTITION BY语句部分，同时指定分区相关的三个核元素：
- 分区类型（partType）：描述分区表的分区策略，分别有RANGE/INTERVAL/LIST/HASH。
- 分区键（partKey）：描述分区表的分区列，目前RANGE/LIST分区支持多列（不超过16列）分区键，INTERVAL/HASH分区只支持单列分区。
- 分区表达式（partExpr）：描述分区表的具体分区表方式，即键值与分区的对应映射关系。
 
这三个重要元素会在建表语句的Partition By Clause子句中体现，具体形式为PARTITION BY partType (partKey) (partExpr\[,partExpr\]...)。基本语法框架示例如下：
```
CREATE TABLE [ IF NOT EXISTS ] partition_table_name
(
    [ /* 该部分继承于普通表的Create Table */
    { column_name data_type [ COLLATE collation ] [ column_constraint [ ... ] ]
    | table_constraint
    | LIKE source_table [ like_option [...] ] }[, ... ]
    ]
)
[ WITH ( {storage_parameter = value} [, ... ] ) ]
[ COMPRESS | NOCOMPRESS ]
[ TABLESPACE tablespace_name ]
/* 范围分区场景，若声明INTERVAL子句则为间隔分区场景 */
PARTITION BY RANGE (partKey) [ INTERVAL ('interval_expr') [ STORE IN (tablespace_name [, ... ] ) ] ] (
    partition_start_end_item [, ... ]
    partition_less_then_item [, ... ]
)
/* 列表分区场景，若声明AUTOMATIC则支持list自动扩展 */
PARTITION BY LIST (partKey) [ AUTOMATIC ]
(
    PARTITION partition_name VALUES (list_values_clause) [ TABLESPACE tablespace_name [, ... ] ]
...
)
/* 哈希分区场景 */
PARTITION BY HASH (partKey) (
    PARTITION partition_name [ TABLESPACE tablespace_name [, ... ] ]
...
)
/* 开启/关闭分区表行迁移 */
[ { ENABLE | DISABLE } ROW MOVEMENT ];
```
规格约束：
- RANGE/LIST分区最大支持16个分区键，INTERVAL/HASH分区均只支持1个分区键。
- INTERVAL分区仅支持数值类型和日期/时间类型。
- INTERVAL分区表定义不能有MAXVALUE分区，LIST自动扩展分区表不能定义有DEFAULT分区。
- 除哈希分区外，分区键不能插入空值，否则DML语句会进行报错处理。唯一例外：RANGE分区表定义有MAXVALUE分区/LIST分区表定义有DEFAULT分区。
 
#### 创建二级分区表
二级分区表，可以看成是对一级分区表的扩展，在二级分区表中，第一层分区是一张逻辑表，并不实际存储数据，数据实际是存储在二级分区节点上的。从实现上而言，二级分区表的分区方案是由两个一级分区的嵌套而来，一级分区的分区方案详见《参考》中"SQL参考 \> SQL语法 \> C \> CREATE TABLE PARTITION"章节。常见的二级分区表组合方案有：Range-Range分区、Range-List分区、Range-Hash分区、List-Range分区、List-List分区、List-Hash分区、Hash-Range分区、Hash-List分区、Hash-Hash分区等。目前二级分区仅支持行存表，二级分区创建的基本语法框架示例如下：
```
CREATE TABLE [ IF NOT EXISTS ] subpartition_table_name
(
    [ /* 该部分继承于普通表的Create Table */
    { column_name data_type [ COLLATE collation ] [ column_constraint [ ... ] ]
    | table_constraint
    | LIKE source_table [ like_option [...] ] } [, ... ]
    ]
)
[ WITH ( {storage_parameter = value} [, ... ] ) ]
[ COMPRESS | NOCOMPRESS ]
[ TABLESPACE tablespace_name ]
/* 二级分区定义的部分，只有list分区策略支持声明AUTOMATIC */
PARTITION BY {RANGE | LIST | HASH} (partKey) [ AUTOMATIC ] SUBPARTITOIN BY {RANGE | LIST | HASH} (partKey) [ AUTOMATIC ]
(
    PARTITION partition_name partExpr…  /* 第一层分区 */
    (
        SUBPARTITION partition_name partExpr … /* 第二层分区 */
        SUBPARTITION partition_name partExpr … /* 第二层分区 */
    ),
    PARTITION partition_name partExpr…  /* 第一层分区 */
    (
        SUBPARTITION partition_name partExpr … /* 第二层分区 */
        SUBPARTITION partition_name partExpr … /* 第二层分区 */
    ),
    …
)
[ { ENABLE | DISABLE } ROW MOVEMENT ];
```
非透明多写规格约束：
- 二级分区表支持LIST/HASH/RANGE分区的任意两两组合。
- 二级分区表支持任一层LIST声明自动扩展。
- 二级分区表的第二层分区采用LIST自动扩展时，建表语句中第二层分区定义不能为空。
 
#### 修改分区属性
分区表和分区相关的部分属性可以使用类似非分区表的ALTER-TABLE命令进行分区属性修改，常用的分区属性修改语句包括：
- 增加分区
- 删除分区
- 删除/清空分区数据
- 切割分区
- 合并分区
- 移动分区
- 交换分区
- 重命名分区
 
以上常用的分区属性变更语句基于对普通表ALTER TABLE语句进行扩展，在使用方式上大部分使用方式类似，分区表属性变更的基本语法框架示例如下：
```
/* 基本alter table语法 */
ALTER TABLE [ IF EXISTS ] { table_name [*] | ONLY table_name | ONLY ( table_name )}
action [, ... ];
```
分区表ALTER TABLE语句使用方法请参见[分区表运维管理](https://support.huaweicloud.com/centralized-devg-v10-gaussdb/gaussdb-42-0529.html)、《参考》中"SQL参考 \> SQL语法 \> A \> ALTER TABLE PARTITION"和"SQL参考 \> SQL语法 \> A \> ALTER TABLE SUBPARTITION"章节。
