直接在select后写表达式可计算字段值,但必须用as指定别名;算术运算需注意null传播、整数除法差异、字符串类型限制;字符串拼接应优先使用通用concat()函数;where中不可用计算字段别名,须重复表达式或用cte;跨表计算要处理空值,join条件避免复杂逻辑;括号和别名格式易引发隐性错误。

直接在 SELECT 后写表达式就能计算字段值,不需要函数包装、不依赖子查询——但必须加 AS 别名,否则结果列名不可靠,下游代码很可能取不到值。
算术运算:+ − * / 直接用,但 NULL 和类型要盯紧
字段参与四则运算最常见,比如 price * quantity 算小计、base_salary + bonus 算实发。但有三个硬约束:
- 只要任一操作数为
NULL,整个结果就是NULL(不是 0,不是空字符串);得用COALESCE(price, 0)或IFNULL(quantity, 0)显式兜底 - 整数除法行为不统一:
7 / 3在 PostgreSQL 和 SQL Server 中返回2,MySQL 可能返回2.3333;要小数就写成7.0 / 3或CAST(7 AS DECIMAL) / 3 - 字符串字段不能直接参与算术运算;
status + 1在 PostgreSQL 会报operator does not exist: text + integer,MySQL 可能静默转成 0 再加,结果不可信
字符串拼接:不同数据库语法不兼容,别用 +
+ 运算符在各库语义混乱:SQL Server 允许字符串拼接,PostgreSQL 和 SQLite 只认数值加法。必须按数据库选函数或操作符:
- MySQL:用
CONCAT(name, ' (', dept, ')') - PostgreSQL:用
name || ' (' || dept || ')' - SQL Server:用
name + ' (' + dept + ')'(仅当字段是字符串类型时安全) - 通用写法(推荐):所有库都支持
CONCAT(),且自动跳过NULL值,比||或+更稳
WHERE 和 ORDER BY 里不能直接用计算字段别名
SELECT price * 1.1 AS final_price FROM products WHERE final_price > 100 会报错——因为 SQL 执行顺序是 WHERE → SELECT,final_price 此时还没生成。可行方案只有两个:
- 在
WHERE中重复表达式:WHERE price * 1.1 > 100 - 用 CTE 或子查询封装计算逻辑:
WITH calc AS (SELECT id, price * 1.1 AS final_price FROM products) SELECT * FROM calc WHERE final_price > 100 -
ORDER BY多数库支持别名(如ORDER BY final_price DESC),但 SQLite 不支持,得重写表达式
跨表计算字段:JOIN 后直接运算,但空值要提前处理
从 orders 表取 quantity、从 products 表取 price,做 o.quantity * p.price 是标准做法。关键点在连接方式和空值:
- 用
LEFT JOIN时,若p.price为NULL,乘积必为NULL;应写成o.quantity * COALESCE(p.price, 0) - 避免用
INNER JOIN隐式过滤掉价格缺失的订单,除非业务明确要求只算完整数据 - 别在 JOIN 条件里写计算逻辑(如
ON o.product_id = p.product_id AND p.price > 0),这会让优化器难生效,优先移到WHERE
最容易被忽略的是括号和优先级:discount + price * rate 和 (discount + price) * rate 差一个数量级;还有别名里带空格或连字符时没加双引号,导致语法错误——这些细节不报大错,但查起来极耗时间。











