在 达梦数据库(DM Database) 里,并没有像 SPLIT
这样的内置函数(类似 MySQL 的 SUBSTRING_INDEX
或 Oracle 的 REGEXP_SUBSTR
)可以直接把字符串拆分成数组或多行。
但是你可以通过以下几种方式来实现 字符串分割 的效果:
1. 利用 INSTR
+ SUBSTR
手动查找分隔符位置,截取子串。例如:
-- 假设要按逗号分割
SELECT SUBSTR('A,B,C', 1, INSTR('A,B,C', ',') - 1) AS part1,
SUBSTR('A,B,C', INSTR('A,B,C', ',') + 1, LENGTH('A,B,C')) AS part2
FROM dual;
这种方法适合已知分隔数量的场景。
2. 使用递归 CTE 模拟 Split
可以把一个字符串递归拆成多行:
WITH RECURSIVE split_cte AS (
SELECT SUBSTR('A,B,C,D', 1, INSTR('A,B,C,D', ',') - 1) AS val,
SUBSTR('A,B,C,D', INSTR('A,B,C,D', ',') + 1) AS rest
FROM dual
UNION ALL
SELECT CASE WHEN INSTR(rest, ',') > 0
THEN SUBSTR(rest, 1, INSTR(rest, ',') - 1)
ELSE rest END,
CASE WHEN INSTR(rest, ',') > 0
THEN SUBSTR(rest, INSTR(rest, ',') + 1)
ELSE '' END
FROM split_cte
WHERE rest <> ''
)
SELECT val FROM split_cte;
结果:
A
B
C
D
3. 自定义函数(推荐)
你可以用 PL/SQL过程语言(达梦兼容 Oracle PL/SQL) 写一个 Split 函数,返回表类型。
例如:
CREATE OR REPLACE FUNCTION fn_split(str VARCHAR2, delimiter VARCHAR2)
RETURN SYS.ODCIVARCHAR2LIST PIPELINED
AS
pos INT := 1;
idx INT;
tmp VARCHAR2(4000);
BEGIN
LOOP
idx := INSTR(str, delimiter, pos);
IF idx > 0 THEN
tmp := SUBSTR(str, pos, idx - pos);
PIPE ROW(tmp);
pos := idx + LENGTH(delimiter);
ELSE
tmp := SUBSTR(str, pos);
PIPE ROW(tmp);
EXIT;
END IF;
END LOOP;
RETURN;
END;
然后使用:
SELECT * FROM TABLE(fn_split('A,B,C,D', ','));
✅ 总结:
- 达梦数据库没有现成的
SPLIT
函数。 - 你可以用
INSTR+SUBSTR
、递归CTE 或 自定义函数 实现类似功能。