PostgreSQL 教程

PostgreSQL 更新数据

在数据库表中更新数据是数据库管理中极其关键的一环。UPDATE 语句允许你修改表中已存在的旧数据,确保你的数据库能准确反映信息的最新状态。

掌握如何高效、安全地使用 UPDATE 语句,对于维护数据完整性和保持数据库的鲜活性至关重要。

1. UPDATE 语句:基础语法

在 PostgreSQL 中,UPDATE 语句的基础语法如下:

UPDATE table_name
SET column1 = value1, column2 = value2, ...
WHERE condition;

让我们拆解一下这条语句的各个部分:

  • UPDATE table_name: 这指定了你想要修改数据的目标表名。
  • SET column1 = value1, ...: 这一部分定义了你想要更新的列,以及你要赋给它们的新值。你可以通过用逗号分隔每个“列=值”对,在一条 UPDATE 语句中同时更新多个列。
  • WHERE condition: 这是 UPDATE 语句中最致命也是最关键的一部分。它指定了哪些行将会被更新。如果你省略了 WHERE 子句,表中的所有行都将被更新!这通常绝对不是你想要的结果。

基础示例:
假设你有一个名为 employees (员工) 的表,当前数据如下:

employee_idfirst_namelast_namesalary
1JohnDoe50000
2JaneSmith60000
3PeterJones55000

要想把 John Doe 的薪水 (salary) 更新为 52000,你需要使用以下 UPDATE 语句:

UPDATE employees
SET salary = 52000
WHERE employee_id = 1;

执行这条语句后,employees 表中 ID 为 1 的那行数据的薪水就会变成 52000。

2. 同时更新多个列

UPDATE 语句允许你同时修改多个列。只需在 SET 子句中包含多个 列 = 值 的配对,并用逗号隔开即可。

示例:
假设 Jane Smith 结婚了,她的姓氏改为了 Williams,同时她还获得了一次加薪,薪水涨到了 65000。你可以用一条语句同时更新她的姓氏和薪水:

UPDATE employees
SET last_name = 'Williams', salary = 65000
WHERE employee_id = 2;

3. 在 SET 子句中使用数学表达式

你可以在 SET 子句中使用数学表达式,基于现有的数据计算出新的值。这使得进行复杂的批量调整成为可能。

示例:
假设公司决定给 ID 为 3 的员工(Peter Jones)涨薪 5%。你可以使用表达式来计算新薪水:

UPDATE employees
SET salary = salary * 1.05
WHERE employee_id = 3;

(这里 salary * 1.05 也可以写成 salary + (salary * 0.05))

危险警告: 如果你写成了 UPDATE employees SET salary = salary * 1.05;没有 WHERE 子句),那么全公司所有员工的薪水都会瞬间上涨 5%!

4. 结合复杂的 WHERE 条件进行更新

WHERE 子句可以使用逻辑运算符 (AND, OR, NOT) 和比较运算符 (=, !=, >, <, >=, <=) 来构建复杂的过滤条件。这使得你可以精准定位需要更新的特定行。

示例:
假设公司决定给所有当前薪水低于 60000 的员工普调加薪 10%:

UPDATE employees
SET salary = salary * 1.10
WHERE salary < 60000;

在这个例子中,原本薪水是 52000 的 John 和 55000 的 Peter 会获得加薪,而薪水已经是 65000 的 Jane 不受影响。

5. 进阶:使用其他表的数据进行更新

有时你需要根据另一张表中的信息来更新当前表的数据。这通常可以通过子查询 (Subqueries) 或多表关联 (JOINs) 来实现。

5.1 使用子查询 (Subqueries) 进行更新

假设你有一张名为 department_managers (部门经理) 的表,记录了谁是经理:

department_idmanager_id
12

现在你想在 employees 表中更新一个布尔值列 is_manager,标记出哪些员工是经理。

首先,假设你已经添加了这个列:

ALTER TABLE employees ADD COLUMN is_manager BOOLEAN DEFAULT FALSE;

然后,使用子查询进行更新:

UPDATE employees
SET is_manager = TRUE
WHERE employee_id IN (SELECT manager_id FROM department_managers);

这条语句会查找 department_managers 表中的所有经理 ID,并将 employees 表中对应员工的 is_manager 字段设为 TRUE

5.2 使用多表关联 (FROM 子句) 进行更新

在 PostgreSQL 中,当你想基于另一张表的数据更新目标表时,通常使用 FROM 子句和 WHERE 匹配条件,而不是标准的 SQL JOIN 语法。

假设你有一张 departments (部门) 表:

department_iddepartment_namebonus_percentage (奖金比例)
1Sales0.05
2Marketing0.10

假设 employees 表中已经有了 department_id 列,标记了每个员工所属的部门。现在你想根据他们各自部门的奖金比例,计算并发放奖金(更新到薪水里)。

正确的 PostgreSQL 语法:

UPDATE employees
SET salary = employees.salary * (1 + departments.bonus_percentage)
FROM departments
WHERE employees.department_id = departments.department_id;

在这个查询中,PostgreSQL 巧妙地将 employees 表和 departments 表通过 WHERE 子句中的 department_id 连接起来,并动态地为每个员工应用其对应部门的奖金比例。