EXTRACT(YEAR FROM date)是SQL标准函数,在PostgreSQL等兼容SQL:2003的数据库中统一使用,要求date为TIMESTAMP或DATE类型、YEAR大写不加引号;MySQL不支持该语法而用YEAR(),SQL Server需用DATEPART(YEAR, date),跨库无通用写法。

EXTRACT(YEAR FROM ...) 在 PostgreSQL 和标准 SQL 中怎么写
PostgreSQL 和支持 SQL:2003 标准的数据库(如 DuckDB、BigQuery)用 EXTRACT 提取年份,语法统一且直观。它把时间戳当参数,返回整数年份值。
常见错误是把字段名漏掉或错写成字符串字面量——EXTRACT(YEAR FROM '2023-05-01') 在某些引擎里会报类型错误,因为没明确时区或类型推导失败;应确保输入是 TIMESTAMP 或 DATE 类型。
-
SELECT EXTRACT(YEAR FROM created_at) AS year FROM orders;—— 正确,假设created_at是TIMESTAMP WITH TIME ZONE - 如果字段是文本型(如
TEXT),必须先转:EXTRACT(YEAR FROM TO_TIMESTAMP(created_at, 'YYYY-MM-DD HH24:MI:SS')) - 注意时区影响:
EXTRACT(YEAR FROM TIMESTAMP '2023-12-31 23:00:00+00')返回2023,但同一时刻在+08时区已是 2024 年 1 月 1 日 07:00,AT TIME ZONE 'Asia/Shanghai'后再提取才反映本地年份
DATEPART(YEAR, ...) 在 SQL Server 和 Azure Synapse 中的写法
SQL Server 不支持 EXTRACT,必须用 DATEPART,函数名和参数顺序都不同,且第一个参数是部件名(字符串),第二个才是日期表达式。
容易踩的坑是大小写混淆(虽然 SQL Server 不区分,但写成 datepart(year, ...) 容易被误认为是其他方言),以及误把 YEAR 当函数调用(如 YEAR(date_col) 虽然也能用,但 DATEPART 更通用,支持更多部件如 ISO_WEEK)。
-
SELECT DATEPART(YEAR, order_date) AS year FROM sales;—— 最常用写法 - 不能写成
DATEPART('YEAR', ...),单引号会导致解析为字符串字面量而非日期部件标识符 - 对
NULL输入,DATEPART返回NULL,不是 0 或报错,这点和EXTRACT行为一致
MySQL 没有 EXTRACT(YEAR) 或 DATEPART,得用 YEAR()
MySQL 完全不支持 EXTRACT 的标准语法(虽然 8.0+ 加了部分兼容,但 EXTRACT(YEAR FROM ...) 仍不可用),也不提供 DATEPART。唯一可靠方式是 YEAR() 函数,它接受 DATE、DATETIME 或有效字符串(如 '2023-06-15')。
风险点在于隐式转换:若字段是 VARCHAR 存储时间(比如 '2023/06/15'),YEAR(col) 可能返回 0 或警告,取决于 SQL mode;建议显式用 STR_TO_DATE(col, '%Y/%m/%d') 转换后再取年。
-
SELECT YEAR(shipment_time) AS year FROM logistics;—— 简洁有效 -
YEAR(NOW())返回当前年,YEAR('2023-01-01')也合法 - 别用
EXTRACT(YEAR FROM ...),MySQL 会报错FUNCTION xxx.EXTRACT does not exist
跨数据库可移植的写法其实不存在
没有一种语法能在 PostgreSQL、SQL Server、MySQL、SQLite、Oracle 之间通用。哪怕看起来相似的 EXTRACT,Oracle 要求写成 EXTRACT(YEAR FROM date_col)(支持),而 SQLite 根本不支持该函数,只能靠 strftime('%Y', date_col)。
真正要兼容多个后端时,不能依赖单个函数,得在应用层判断方言,或用 ORM 的抽象(如 SQLAlchemy 的 extract('year', col) 会自动翻译)。硬写 SQL 时,最稳妥的是按目标数据库选对应函数,而不是试图“一次编写到处运行”。
年份提取本身简单,但背后的时间类型处理、时区上下文、空值行为、输入格式校验,才是真正消耗调试时间的地方。

















