---
title: "UPDATE | OceanBase 文档中心"
description: UPDATE UPDATE 算子用于更新数据表中满足指定条件的数据行。 OceanBase 数据库支持的 UPDATE 算子包括 UPDATE 和 MULTI PARTITION UPDATE 。 UPDATE UPDATE 算子用于更新数据表单个分区中的数据。 如下例所示，Q1 查询更新了表 t1 中所有满足 c2…
---
切换语言

- 中文站 - 简体中文
- International - English
- 日本站 - 日本語

文档反馈![](https://mdn.alipayobjects.com/huamei_22khvb/afts/img/A*P8CuR4UJ_FkAAAAAAAAAAAAADiGDAQ/original) OceanBase 数据库分布式版 - V 3.2.3 企业版 LTS

# UPDATE

更新时间：2025-07-04 15:35:55

`UPDATE` 算子用于更新数据表中满足指定条件的数据行。

OceanBase 数据库支持的 `UPDATE` 算子包括 `UPDATE` 和 `MULTI PARTITION UPDATE`。

## UPDATE

`UPDATE` 算子用于更新数据表单个分区中的数据。

如下例所示，Q1 查询更新了表 `t1` 中所有满足 `c2 = '100'` 的行，并将 `c2` 列的值设置为 200。

```javascript
obclient> CREATE TABLE t1 (c1 INT PRIMARY KEY, c2 VARCHAR2(10));
Query OK, 0 rows affected

obclient> CREATE TABLE t2 (c1 INT PRIMARY KEY, c2 VARCHAR2(10)) PARTITION BY
        HASH(c1) PARTITIONS 10;
Query OK, 0 rows affected

obclient> CREATE TABLE t3 (c1 INT PRIMARY KEY, c2 VARCHAR2(10));
Query OK, 0 rows affected

obclient> CREATE INDEX IDX_t3_c2 ON t3 (c2) PARTITION BY HASH(c2) PARTITIONS 3;
Query OK, 0 rows affected

Q1:
obclient> EXPLAIN UPDATE t1 SET c2 = '200' WHERE c2 = '100'\G
*************************** 1. row ***************************
Query Plan:
======================================
|ID|OPERATOR            |NAME|EST. ROWS|COST  |
-----------------------------------------------
|0 |EXCHANGE IN REMOTE  |    |990      |109687|
|1 | EXCHANGE OUT REMOTE|    |990      |109687|
|2 |  UPDATE            |    |990      |109687|
|3 |   TABLE SCAN       |T1  |990      |108697|
===============================================

Outputs & filters:
-------------------------------------
  0 - output(nil), filter(nil)
  1 - output(nil), filter(nil)
  2 - output(nil), filter(nil), table_columns([{T1: ({T1: (T1.C1, T1.C2)})}]),
      update([T1.C2=?])
  3 - output([T1.C1], [T1.C2], [?]), filter([T1.C2 = '100']),
      access([T1.C2], [T1.C1]), partitions(p0)

```

上述示例中，执行计划展示中的 `outputs & filters` 详细列出了 `UPDATE` 算子的输出信息如下：

| **信息名称** | **含义** |
| --- | --- |
| output | 该算子输出的表达式。 |
| filter | 该算子上的过滤条件。由于示例中 `UPDATE` 算子没有 `filter`，所以为 `nil`。对于更新语句，`WHERE` 中的谓词会下推到基表上，比如 Q1 查询中的 `c2 = '100'` 被下推到了 1 号算子上。 |
| table_columns | 更新操作涉及的数据表的列。 |
| update | 更新操作中所有的赋值表达式。 |

更多 `UPDATE` 算子的示例如下：

- Q2 查询更新 `t1` 表中的所有数据行，并将 `c2` 列的值置为 200。
 - Q3 查询更新分区表 `t2` 中满足 `c1='100'` 的数据行，并将 `c2` 列的值置为 150。
 - Q4 查询更新分区表 `t2` 中满足 `c2 ='100'` 的数据行，并将 `c2` 列的值置为 `rpad(t2.c2, 10, '9')`。从执行计划中可以看到，`UPDATE` 算子分配在 `EXCHANGE` 算子下面，因此 2 号和 3 号算子会作为一个任务以分区的粒度进行调度。执行时 4 号算子扫描出 `t2` 一个分区中满足 `c2 = '100'` 的数据，3 号 `UPDATE` 算子则只会更新相应分区下扫描出的数据。

```javascript
Q2:
obclient> EXPLAIN UPDATE t1 SET c2 = '200'\G
*************************** 1. row ***************************
Query Plan:
======================================
|ID|OPERATOR            |NAME|EST. ROWS|COST  |
-----------------------------------------------
|0 |EXCHANGE IN REMOTE  |    |100000   |161860|
|1 | EXCHANGE OUT REMOTE|    |100000   |161860|
|2 |  UPDATE            |    |100000   |161860|
|3 |   TABLE SCAN       |T1  |100000   |61860 |
===============================================

Outputs & filters:
-------------------------------------
  0 - output(nil), filter(nil)
  1 - output(nil), filter(nil)
  2 - output(nil), filter(nil), table_columns([{T1: ({T1: (T1.C1, T1.C2)})}]),
      update([T1.C2=?])
  3 - output([T1.C1], [T1.C2], [?]), filter(nil),
      access([T1.C2], [T1.C1]), partitions(p0)

Q3:
obclient> EXPLAIN UPDATE t2 SET t2.c2 = '150' WHERE t2.c1 = '100'\G
*************************** 1. row ***************************
Query Plan:
===================================
|ID|OPERATOR  |NAME|EST. ROWS|COST|
-----------------------------------
|0 |UPDATE    |    |1        |53  |
|1 | TABLE GET|T2  |1        |52  |
===================================

Outputs & filters:
-------------------------------------
  0 - output(nil), filter(nil), table_columns([{T2: ({T2: (T2.C1, T2.C2)})}]),
      update([T2.C2=?])
  1 - output([T2.C1], [T2.C2], [?]), filter(nil),
      access([T2.C1], [T2.C2]), partitions(p5)

Q4:
obclient> EXPLAIN UPDATE t2 SET t2.c2 = RPAD(t2.c2, 10, '9')  WHERE t2.c2 = '100'\G
*************************** 1. row ***************************
Query Plan:
===============================================
|ID|OPERATOR               |NAME    |EST. ROWS|COST   |
-------------------------------------------------------
|0 |PX COORDINATOR         |        |9900     |1096793|
|1 | EXCHANGE OUT DISTR    |:EX10000|9900     |1096793|
|2 |  PX PARTITION ITERATOR|        |9900     |1096793|
|3 |   UPDATE              |        |9900     |1096793|
|4 |    TABLE SCAN         |T2      |9900     |1086893|
=======================================================

Outputs & filters:
-------------------------------------
  0 - output(nil), filter(nil)
  1 - output(nil), filter(nil), dop=1
  2 - output(nil), filter(nil)
  3 - output(nil), filter(nil), table_columns([{T2: ({T2: (T2.C1, T2.C2)})}]),
      update([T2.C2=column_conv(VARCHAR,utf8mb4_bin,length:10,NULL,RPAD(T2.C2, 10, ?))])
  4 - output([T2.C1], [T2.C2], [column_conv(VARCHAR,utf8mb4_bin,length:10,NULL,RPAD(T2.C2, 10, ?))]), filter([T2.C2 = '100']),
      access([T2.C1], [T2.C2]), partitions(p[0-9])

```

## MULTI PARTITION UPDATE

`MULTI PARTITION UPDATE` 算子表示更新数据表多个分区中的数据。如下例所示，Q5 查询更新表 `t3` 中所有满足 `c2 < '100'` 的数据行，并将 `c2` 列的值置为 200。虽然 `t3` 本身是一个非分区表，但 `t3` 表上存在全局索引 `idx_t3_c2`，因此每一条数据行会存在于多个分区中。

```javascript
Q5:
obclient> EXPLAIN UPDATE t3 SET c2 = '200' WHERE c2 < '100'\G
*************************** 1. row ***************************
Query Plan:
========================================================
|ID|OPERATOR                |NAME         |EST. ROWS|COST |
-----------------------------------------------------------
|0 |MULTI PARTITION UPDATE  |             |10001    |27780|
|1 | PX COORDINATOR         |             |10001    |17780|
|2 |  EXCHANGE OUT DISTR    |:EX10000     |10001    |14941|
|3 |   PX PARTITION ITERATOR|             |10001    |14941|
|4 |    TABLE SCAN          |T3(IDX_T3_C2)|10001    |14941|
===========================================================

Outputs & filters:
-------------------------------------
  0 - output(nil), filter(nil), table_columns([{T3: ({T3: (T3.C1, T3.C2)}, {IDX_T3_C2: (T3.C2, T3.C1)})}]),
      update([T3.C2=?])
  1 - output([T3.C1], [T3.C2], [?]), filter(nil)
  2 - output([T3.C2], [T3.C1], [?]), filter(nil), dop=1
  3 - output([T3.C2], [T3.C1], [?]), filter(nil)
  4 - output([T3.C2], [T3.C1], [?]), filter(nil),
      access([T3.C2], [T3.C1]), partitions(p[0-2])

```

更多 `MULTI PARTITION UPDATE` 的示例如下：

- Q6 查询更新分区表 `t2` 中满足 `c1 = 100` 的数据行，并将 `c1` 列的值设置为 101。因为更新的列是主键列，可能会导致更新后的数据行与更新前的数据行位于不同的分区，因此需要使用 `MULTI PARTITION UPDATE` 算子进行更新。

```javascript
Q6:
obclient> EXPLAIN UPDATE t2 SET t2.c1 = 101 WHERE t2.c1 = 100\G
*************************** 1. row ***************************
Query Plan:
===============================================
|ID|OPERATOR              |NAME|EST. ROWS|COST|
-----------------------------------------------
|0 |MULTI PARTITION UPDATE|    |1        |54  |
|1 | EXCHANGE IN DISTR    |    |1        |53  |
|2 |  EXCHANGE OUT DISTR  |    |1        |52  |
|3 |   TABLE GET          |T2  |1        |52  |
===============================================

Outputs & filters:
-------------------------------------
  0 - output(nil), filter(nil), table_columns([{T2: ({T2: (T2.C1, T2.C2)})}]),
      update([T2.C1=?])
  1 - output([T2.C1], [T2.C2], [?]), filter(nil)
  2 - output([T2.C1], [T2.C2], [?]), filter(nil)
  3 - output([T2.C1], [T2.C2], [?]), filter(nil),
      access([T2.C1], [T2.C2]), partitions(p5)

```

 上一篇 下一篇 ![有帮助](https://gw.alipayobjects.com/mdn/ob_asset/afts/img/A*y6ocSqN8cqsAAAAAAAAAAAAAARQnAQ)![无帮助](https://gw.alipayobjects.com/mdn/ob_asset/afts/img/A*BG9IQJyLHF8AAAAAAAAAAAAAARQnAQ)![反馈](https://gw.alipayobjects.com/mdn/ob_asset/afts/img/A*eTWdQKCRKHwAAAAAAAAAAAAAARQnAQ)[AI](https://www.oceanbase.com/obi) 咨询热线
