Blu*_*ark 5 sybase t-sql sybase-sql-anywhere string-splitting
我有场 id_list='1234,23,56,576,1231,567,122,87876,57553,1216'
我想用它来搜索IN
这个领域:
SELECT *
FROM table1
WHERE id IN (id_list)
Run Code Online (Sandbox Code Playgroud)
id
是 integer
id_list
是 varchar/text
但是这样就行不通了,所以我需要以某种方式拆分id_list
为选择查询。
我应该在这里使用什么解决方案?我正在使用 T-SQL Sybase ASA 9 数据库 (SQL Anywhere)。但是这样就行不通了,所以我需要以某种方式拆分id_list
为选择查询。
我看到的方式是使用while循环创建自己的函数,并根据分隔符位置搜索拆分每个元素提取,然后将元素插入到临时表中,该函数将作为结果返回。
对 Sebastian Meine 回答及其解决方案的评论:
Sybase SQL Anywhere 9
sa_split_list
系统程序在这里不存在,所以它不起作用
CAST
效果很好Sybase SQL Anywhere 12
sa_split_list
系统程序存在并且运行良好
CAST
效果很好对于 Sybase SQL Anywhere 9,我进行了 sa_split_list 系统过程替换:
Run Code Online (Sandbox Code Playgroud)CREATE PROCEDURE str_split_list(in str long varchar, in delim char(10) default ',') RESULT( line_num integer, row_value long varchar) BEGIN DECLARE str2 long varchar; DECLARE position integer; CREATE TABLE #str_split_list ( line_num integer DEFAULT AUTOINCREMENT, row_value long varchar null, primary key(line_num)); SET str = TRIM(str)+delim; SET position = CHARINDEX(delim, str); separaterows: WHILE position > 0 loop SET str2 = TRIM(LEFT(str, position - 1)); INSERT INTO #str_split_list (row_value) VALUES (str2); SET str = RIGHT(str, LENGTH(str) - position); SET position = CHARINDEX(delim, str); end loop separaterows; select * from #str_split_list order by line_num asc; END
执行方式与 sa_split_list 相同:
Run Code Online (Sandbox Code Playgroud)select * from str_split_list('1234,23,56,576,1231,567,122,87876,57553,1216')
我实际上没有要测试的 sybase 系统,但是根据 http://dcx.sybase.com/1200/en/dbreference/sa-split-list-sysproc.html,以下解决方案应该有效:
SELECT *
FROM table AS T
JOIN sa_split_list('1234,23,56,576,1231,567,122,87876,57553,1216') AS L
ON T.id = L.row_value;
Run Code Online (Sandbox Code Playgroud)
如果 id_list 实际上存储在另一个表(比如 list_table)中,您还需要使用CROSS APPLY
运算符 ( http://dcx.sybase.com/1101/en/dbusage_en11/apply-joins-joinsasp.html):
SELECT *
FROM list_table AS LT
CROSS APPLY sa_split_list(LT.id_list) L
JOIN table T
ON T.id = L.row_value
AND <optional: some other condition that ties rows in list_table to rows in table, like a group membership or location>
Run Code Online (Sandbox Code Playgroud)
这一切都要求只有数字是这些列表的一部分,因为拆分的部分将自动转换为 id 列的数据类型。如果不是这种情况,您可以使用这种更简单但速度较慢的技术:
SELECT *
FROM table
WHERE ','+@id_list+',' LIKE '%,'+CAST(id AS VARCHAR(20))+',%'
Run Code Online (Sandbox Code Playgroud)
最后一个例子假设 id 列表在变量@id_list 中。如果它在另一个表中,您可以使用CROSS APPLY
上面相同的技术。附加逗号确保第一个或最后一个条目可以匹配。