小巧、快速、可靠。
三者选其二。
删除

1. 概述

delete-stmt

WITH RECURSIVE common-table-expression , DELETE FROM qualified-table-name returning-clause expr WHERE

common-table-expression

expr

qualified-table-name

returning-clause

DELETE 命令从由 qualified-table-name 标识的表中删除记录。

如果 WHERE 子句不存在,则删除表中的所有记录。如果提供 WHERE 子句,则仅删除 WHERE 子句 布尔表达式 为真的行。表达式为假或 NULL 的行将保留。

2. CREATE TRIGGER 中 DELETE 语句的限制

以下限制适用于在 CREATE TRIGGER 语句主体中出现的 DELETE 语句

3. 可选的 LIMIT 和 ORDER BY 子句

如果 SQLite 使用 SQLITE_ENABLE_UPDATE_DELETE_LIMIT 编译时选项进行编译,则 DELETE 语句的语法将通过添加可选的 ORDER BY 和 LIMIT 子句来扩展

delete-stmt-limited

WITH RECURSIVE common-table-expression , DELETE FROM qualified-table-name WHERE expr returning-clause ORDER BY ordering-term , LIMIT expr OFFSET expr , expr

如果 DELETE 语句具有 LIMIT 子句,则将通过评估伴随的表达式并将其转换为整数值来找到将被删除的最大行数。如果评估 LIMIT 子句的结果不能无损地转换为整数值,则将发生错误。负 LIMIT 值将解释为“无限制”。如果 DELETE 语句还具有 OFFSET 子句,则类似地对其进行评估并将其转换为整数值。同样,如果该值不能无损地转换为整数,则会发生错误。如果没有 OFFSET 子句,或者计算出的整数值为负,则有效 OFFSET 值为零。

如果 DELETE 语句具有 ORDER BY 子句,则在应用 LIMIT 和 OFFSET 子句以确定实际删除的子集之前,将根据 ORDER BY 对在没有 LIMIT 子句的情况下将被删除的所有行进行排序。跳过前 M 行(其中 M 是通过评估 OFFSET 子句表达式找到的值),并删除接下来的 N 行(其中 N 是 LIMIT 表达式的值)。如果在考虑 OFFSET 子句后剩余的行少于 N 行,或者如果 LIMIT 子句评估为负值,则删除所有剩余的行。

如果 DELETE 语句没有 ORDER BY 子句,则在应用 LIMIT 和 OFFSET 子句以确定实际删除的子集之前,将以任意顺序组装在没有 LIMIT 子句的情况下将被删除的所有行。

DELETE 语句上的 ORDER BY 子句仅用于确定哪些行位于 LIMIT 范围内。删除行的顺序是任意的,不受 ORDER BY 子句的影响。这意味着,如果存在 RETURNING 子句,则语句返回的行可能不会按 ORDER BY 子句指定的顺序排列。

4. 截断优化

当从 DELETE 语句中同时省略 WHERE 子句和 RETURNING 子句时,并且被删除的表没有触发器,SQLite 使用一种优化来擦除整个表内容,而无需逐个访问表的每行。这种“截断”优化使删除操作运行得更快。在 SQLite 版本 3.6.5(2008-11-12)之前,截断优化还意味着 sqlite3_changes()sqlite3_total_changes() 接口以及 count_changes pragma 实际上不会返回已删除的行数。从 版本 3.6.5(2008-11-12)开始,已修复该问题。

可以通过使用 SQLITE_OMIT_TRUNCATE_OPTIMIZATION 编译时开关重新编译 SQLite 来永久禁用所有查询的截断优化。

也可以使用 sqlite3_set_authorizer() 接口在运行时禁用截断优化。如果授权器回调针对 SQLITE_DELETE 操作代码返回 SQLITE_IGNORE,则 DELETE 操作将继续执行,但将绕过截断优化,并且将逐个删除行。

本页最后修改于 2022-01-08 05:02:57 UTC