SQL 方言通

首页 / 工具 / 迁移清单 / MaxCompute → Hologres

MaxCompute 迁移到 Hologres 的函数改写清单

从 MaxCompute 迁移到 Hologres 时,在 MaxCompute 有对应写法的 45 个常用函数中,29 个需要改写(其中 2 个在 Hologres 没有对应函数)。逐个列出两边写法和注意事项。

需要改写的函数 · 迁移注意事项 · 可以直接用的函数 · 反向:Hologres 迁移到 MaxCompute

需要改写的函数

函数MaxCompute 写法Hologres 写法Hologres 说明
ADD_MONTHSADD_MONTHS(startdate, num_months)需改写 d + interval '1 month'ADD_MONTHS 是 Oracle 兼容函数,需要先加载 orafce 扩展。原生写法用 interval 加减。
ANY_VALUEANY_VALUE(colname)需改写 MAX(col)通用聚合函数中没有 ANY_VALUE。组内值都相同时,可以用 MAX 或 MIN 代替。
APPROX_COUNT_DISTINCTAPPROX_DISTINCT(colname)支持 APPROX_COUNT_DISTINCT(column)基于 HyperLogLog,平均误差 0.1%~1%。精度由 hg_experimental_approx_count_distinct_precision 控制,取值 12~20,默认 17。精确去重也可以用 UNIQ,它在带 GROUP BY 时比 COUNT DISTINCT 快。
COLLECT_LISTCOLLECT_LIST(colname)需改写 ARRAY_AGG(expression)没有 COLLECT_LIST,用 ARRAY_AGG。
COLLECT_SETCOLLECT_SET(colname)需改写 ARRAY_AGG(DISTINCT expression)没有 COLLECT_SET,用 ARRAY_AGG。不支持 JSON、JSONB、INTERVAL 和数组等类型。
DATE_ADDDATE_ADD(startdate, delta)需改写 DATEADD(d, num, 'day')文档中没有 DATE_ADD,可以用 DATEADD 或 d + interval。DATEADD 需要 V2.0.31~V2.1.0 或 V2.1.13 及以上版本。
DATE_FORMATDATE_FORMAT(date, format)需改写 TO_CHAR(timestamp, 'YYYY-MM-DD HH24:MI:SS')文档中没有 DATE_FORMAT,用 TO_CHAR 代替。格式符是 PostgreSQL 风格,HH 默认是 12 小时制,24 小时制要写 HH24。
DATE_SUBDATE_SUB(startdate, delta)需改写 d - interval '1 day'文档中没有 DATE_SUB。可以用日期减 interval,也可以写 DATEADD(d, -n, 'dd')。DATEADD 需要 V2.0.31~V2.1.0 或 V2.1.13 及以上版本。
DATETRUNCDATETRUNC(date, date_part)需改写 DATE_TRUNC('month', ts)单位在前,返回 TIMESTAMP 或 TIMESTAMPTZ。
DAYOFWEEKDAYOFWEEK(date)需改写 EXTRACT(DOW FROM ts) + 1DOW 以周日为 0,所以要加 1 才和其他引擎一致。ISODOW 以周一为 1、周日为 7。
DECODEDECODE(expression, search, result[, search, result]...[, default])需改写 CASE expr WHEN search THEN result ... ELSE default END条件函数文档中没有 DECODE,用 CASE 改写。
EXPLODEEXPLODE(var)需改写 UNNEST(anyarray)把数组的每个元素展开成一行。
FROM_JSONfrom_json(jsonStr, schema)需改写 json_str::jsonb ->> 'key'没有 FROM_JSON。先转成 JSON 或 JSONB,再用 -> 或 ->> 取字段,->> 返回 TEXT。需要展开成多列时可以用 json_populate_record。
FROM_UNIXTIMEFROM_UNIXTIME(unixtime)需改写 TO_TIMESTAMP(seconds)文档中没有 FROM_UNIXTIME。TO_TIMESTAMP(double precision) 按秒转换,返回 TIMESTAMPTZ。需要字符串时再用 TO_CHAR。
GETDATEGETDATE()别名 NOW() 或 CURRENT_TIMESTAMP返回当前事务的开始时刻,NOW、CURRENT_TIMESTAMP 和 TRANSACTION_TIMESTAMP 等效。需要每次调用都取实时时刻时用 CLOCK_TIMESTAMP。
INSTRINSTR(str1, str2[, start_position[, nth_appearance]])需改写 STRPOS(str, substr)INSTR 是 Oracle 兼容函数,需要先安装 orafce 扩展才能用,支持起始位置和第 N 次出现。不装扩展时用 STRPOS。
MONTHS_BETWEENMONTHS_BETWEEN(end_date, start_date)需改写 (EXTRACT(YEAR FROM a) - EXTRACT(YEAR FROM b)) * 12 + EXTRACT(MONTH FROM a) - EXTRACT(MONTH FROM b)日期函数中没有 MONTHS_BETWEEN,可以用 EXTRACT 取年和月计算整数月差,不含小数部分。
NVLNVL(value, default_value)需改写 COALESCE(value, default_value)条件函数文档中没有 NVL,只有 COALESCE、IF、NULLIF 等,需要改写为 COALESCE。
PERCENTILE_APPROXPERCENTILE_APPROX(col[, weight], p[, B])需改写 APPROX_PERCENTILE(p) WITHIN GROUP (ORDER BY col)Hologres V3.1 起提供,用蓄水池抽样计算,最多保留 8,192 个元素。p 是 0~1 之间的常量。
REGEXP_EXTRACTREGEXP_EXTRACT(source, pattern[, group_id])需改写 (REGEXP_MATCH(str, pattern))[n]字符串函数中没有 REGEXP_EXTRACT。REGEXP_MATCH 返回由各分组组成的数组,再用数组下标取第 n 组,下标从 1 开始。
SIZESIZE(array_or_map)需改写 ARRAY_LENGTH(arr, 1)第二个参数是维度,从 1 开始,一维数组传 1。数组函数文档只覆盖 ARRAY。
SORT_ARRAYSORT_ARRAY(a[, isasc])需改写 ARRAY_SORT(anyarray)只有升序。V1.1.46 起支持 TEXT 数组,但会先转成 INT8 再排序;V1.3.18 起 TEXT 数组按字典序排序,并支持 INT4、INT8、FLOAT4、FLOAT8 和 BOOLEAN 数组。
SPLITSPLIT(source, delimiter[, trimTailEmpty])需改写 REGEXP_SPLIT_TO_ARRAY(str, pattern)字符串函数中没有 SPLIT。拆成数组用 REGEXP_SPLIT_TO_ARRAY,只取第 n 段用 SPLIT_PART(str, delimiter, n)。
STR_TO_MAPSTR_TO_MAP([mapDupKeyPolicy,] text[, delimiter1[, delimiter2]])不支持 字符串函数中没有 STR_TO_MAP。
SUBSTRSUBSTR(str, start_position[, length])需改写 SUBSTRING(str FROM start FOR len)SUBSTR 是 Oracle 兼容函数,需要先加载 orafce 扩展。PostgreSQL 标准写法是 SUBSTRING。
SUBSTRING_INDEXSUBSTRING_INDEX(str, separator, count)不支持 字符串函数中没有 SUBSTRING_INDEX。只取某一段时可以用 SPLIT_PART。
UNIX_TIMESTAMPUNIX_TIMESTAMP(date)需改写 EXTRACT(EPOCH FROM ts)日期函数中没有 UNIX_TIMESTAMP。EXTRACT 的 epoch 字段返回秒数,类型是 DOUBLE PRECISION。
WEEKOFYEARWEEKOFYEAR(date[, date_part])需改写 EXTRACT(WEEK FROM ts)也可以用 week_iso(ts),文档说明语义与 EXTRACT(WEEK FROM ts) 相同、性能更好。返回 DOUBLE PRECISION。
WM_CONCATWM_CONCAT(separator, colname)需改写 STRING_AGG(expression, delimiter)分隔符写在后面,只拼接非 NULL 值。

迁移注意事项

以下内容摘自各函数页中提到 MaxCompute 或 Hologres 的注意事项。

ADD_MONTHS 按月加减

ANY_VALUE 取组内任意值

APPROX_COUNT_DISTINCT 近似去重计数

COLLECT_LIST 聚合为数组

COLLECT_SET 去重聚合为数组

DATE_ADD 日期加减

DATE_FORMAT 日期格式化

DATE_SUB 日期减天数

DATETRUNC 日期截断

DAYOFWEEK 星期几

DECODE 多值匹配

EXPLODE 数组展开为多行

FROM_JSON 按 schema 解析 JSON

FROM_UNIXTIME 时间戳转日期

GETDATE 获取当前时间

INSTR 查找子串位置

MONTHS_BETWEEN 相差月数

NVL 空值替换

PERCENTILE_APPROX 近似分位数

REGEXP_EXTRACT 正则提取

SIZE 数组和 Map 元素个数

SORT_ARRAY 数组排序

SPLIT 字符串拆分

STR_TO_MAP 字符串转 Map

SUBSTR 截取子串

SUBSTRING_INDEX 按分隔符截取

UNIX_TIMESTAMP 日期转时间戳

WEEKOFYEAR 一年中的第几周

WM_CONCAT 分组拼接字符串

可以直接用的函数

下面 16 个函数在两个引擎中写法相同。参数、返回值和边界情况仍可能不同,点开函数页查看细节。

相关页面:MaxCompute 函数写法 · Hologres 函数写法 · 全部迁移清单 · 用 SQL 迁移检查器检查自己的 SQL