我需要在返回列值的同时将某些id值替换为其实际值。并且该列具有多个ID,并以逗号分隔。
我打算使用的当前方法如下,使用嵌套替换:
select
REPLACE(REPLACE(REPLACE('1,2,3','1','One'),'2','Two'),'3','Three') as content_types,
packid,
packsender
from packages;
我总共有6个这样的键值对,所以我需要6个嵌套的替换函数。请提出这是否正确的方法,还有其他更好的方法。
注意:我试图对表格进行归一化,但是有很多其他因素阻止了此操作,因此我必须在不进行归一化的情况下得出该解决方案。
编辑:快速说明:我使用1,2,3作为参考,但是键是5个字符的字母数字唯一组合,因此不会出现任何部分替换的情况。
我具有的样本列数据: CT002,CT004,CT006
我期望输出: ContentType2,ContentType4,ContentType6
谢谢, 维奈。
答案 0 :(得分:0)
在原始帖子中添加了澄清之后,这是解决问题的一种方法。
假设:输入字符串是用逗号分隔的令牌列表(没有多余的空格,制表符等);一些令牌可能等于 CT002 , CT004 或 CT006 ,并且这些令牌必须替换为 ContentType2 , ContentType4 和 ContentType6 ,而其他所有内容保持不变。
这可以使用单个正则表达式来完成。该解决方案易于维护。但是它可能仍然比重复(嵌套)调用REPLACE慢。如果速度成为问题,则应在实际数据上测试这两种方法,以查看哪种方法效果更好。
在我创建的用于测试的示例数据中(在WITH
子句中,该子句不属于SQL查询-使用实际的表名和列名),尤其要注意最后一行-以查看会发生什么情况如果令牌可能包含CT002(例如)作为 substring 。另外,第二行显示令牌 CT002 ,该令牌用空格包围,而不是用逗号立即包围;在这种情况下,它将不会被替换。我通过这些示例来说明以100%的精度和准确性指定数据格式的重要性。
regexp非常简单;您可能不熟悉正则表达式中的 subexpressions ,以及它们在regexp_replace()
的第三个参数中被引用的方式-请参阅相关文档(或搜索“ subexpression”以更广泛的概念使用“正则表达式”)。
with
sample_data (str) as (
select 'ABC3,CT001,CT006,WHYNOT' from dual union all
select 'CT002,CT004, CT006 , CT93' from dual union all
select 'CT002,CT002,CT004,CT002,CT006' from dual union all
select 'ABCT002' from dual
)
select str,
regexp_replace(str, 'CT00(2|4|6)(,|$)', 'ContentType\1\2') as new_str
from sample_data
;
STR NEW_STR
----------------------------- ----------------------------------------------------------------
ABC3,CT001,CT006,WHYNOT ABC3,CT001,ContentType6,WHYNOT
CT002,CT004, CT006 , CT93 ContentType2,ContentType4, CT006 , CT93
CT002,CT002,CT004,CT002,CT006 ContentType2,ContentType2,ContentType4,ContentType2,ContentType6
ABCT002 ABContentType2