字面量是什么
字面量(literal)是直接写在 SQL 文本里的常量:字符串、数字、日期时间、布尔、二进制。它们不来自任何表,由解析器按写法直接判定类型。写法是否规范决定了两件事:同一段脚本能不能在 MySQL 8 与 PostgreSQL 上通用,以及比较时会不会触发隐式类型转换。
基本信息
| 字符串 | 单引号 'abc';内含单引号写成两个:'it''s' |
|---|---|
| 数字 | 整数 42、小数 3.14、科学计数 1e3;数字不加引号 |
| 日期时间 | DATE '2024-01-01'、TIME '10:20:30'、TIMESTAMP '2024-01-01 10:20:30' |
| 布尔 | MySQL 没有独立布尔类型,TRUE/FALSE 等价 1/0;PostgreSQL 有 boolean 类型 |
| 二进制 | MySQL 写 X'41'(值 0x41);PostgreSQL 写 '\x41'::bytea |
| NULL | NULL 是空值标记而非字面量,与任何值比较的结果都是 UNKNOWN |
各类字面量写法
各类字面量写法
SELECT 'hello' AS s, -- 字符串:单引号
42 AS n, -- 整数
3.14 AS f, -- 小数
DATE '2024-01-01' AS d, -- 标准日期字面量
TIMESTAMP '2024-01-01 10:20:30' AS ts, -- 标准时间戳字面量
TRUE AS b -- MySQL 结果 1,PostgreSQL 结果 t
FROM dual; -- PostgreSQL 里去掉 FROM dual典型使用场景
- 写跨库迁移脚本前统一字面量风格,让同一份 SQL 在两库都能解析
- 构造时间边界条件,如 created_at >= TIMESTAMP '2024-01-01 00:00:00'
- 准备测试数据与断言:字面量写错类型会让比较静默不命中
- 给可空列写兜底逻辑时,明确区分 NULL 与空字符串 ''
- 给报表 SQL 的常量加类型前缀,避免依赖各库的隐式转换规则
跨库写法对照
| 写法 | MySQL 8 | PostgreSQL |
|---|---|---|
| 双引号 "abc" | 默认当字符串(除非启用 ANSI_QUOTES) | 当标识符(列名表名),不是字符串 |
| 反引号 `col` | 标识符 | 不识别,直接语法报错 |
| 字符串里的反斜杠 | 默认是转义符,'\n' 表示换行 | 默认是普通字符,要写 E'\n' 才是换行 |
| 嵌入单引号 | '' 或 \' 都可以 | 只能写 ''(标准写法) |
| 日期字面量 | DATE '2024-01-01' 可用 | DATE '2024-01-01' 可用 |
字符串与标识符不要混:MySQL 里 "abc" 会被当成字符串,PostgreSQL 里它是列名。跨库脚本统一用单引号写字符串,用各自的反引号或双引号写标识符。
带时间的列不要拿纯日期字面量做等值比较:created_at = DATE '2024-01-01' 只会命中当天 00:00:00 的行,要按天取数请写成 >= '2024-01-01' AND < '2024-01-02' 的范围条件。