为了放弃阅读整个问题,我的基本问题是:
PostgreSQL中是否有一个函数来转义字符串中的正则表达式字符?
PostgreSQL中是否有一个函数来转义字符串中的正则表达式字符?
我已经探测过文档,但无法找到这样的功能.
这是完整的问题:
在PostgreSQL数据库中,我有一个包含唯一名称的列.我还有一个定期在此字段中插入名称的进程,并且为了防止重复,如果需要输入已存在的名称,它会在末尾附加一个空格和括号.
即姓名,姓名(1),姓名(2),姓名(3)等
就目前而言,我使用以下代码来查找要在系列中添加的下一个数字(用plpgsql编写):
var_name_id := 1; SELECT CAST(substring(a.name from E'\\((\\d+)\\)$') AS int) INTO var_last_name_id FROM my_table.names a WHERE a.name LIKE var_name || ' (%)' ORDER BY CAST(substring(a.name from E'\\((\\d+)\\)$') AS int) DESC LIMIT 1; IF var_last_name_id IS NOT NULL THEN var_name_id = var_last_name_id + 1; END IF; var_new_name := var_name || ' (' || var_name_id || ')';
(var_name包含我要插入的名称.)
这适用于现在,但问题在于WHERE语句:
WHERE a.name LIKE var_name || ' (%)'
此检查不会验证所讨论的%是否为数字,并且它不会考虑多个括号,如“Name((1))”,如果存在任何一种情况,则会抛出强制转换异常.
WHERE语句确实需要更像:
WHERE a.r1_name ~* var_name || E' \\(\\d+\\)'
但var_name可能包含正则表达式字符,这导致上面的问题:PostgreSQL中是否有一个函数可以转义字符串中的正则表达式字符,所以我可以这样做:
WHERE a.r1_name ~* regex_escape(var_name) || E' \\(\\d+\\)'
非常感谢任何建议,包括可能重复我的重复名称解决方案.
如何尝试这样的东西,用var_name替换我的硬编码’John Bernard’:
create table my_table(name text primary key); insert into my_table(name) values ('John Bernard'),('John Bernard (1)'),('John Bernard (2)'),('John Bernard (3)'); select max(regexp_replace(substring(name,13),' |\(|\)','','g')::integer+1) from my_table where substring(name,1,12)='John Bernard' and substring(name,13)~'^ \([1-9][0-9]*\)$'; max ----- 4 (1 row)
一个警告:我假设在此过程运行时单用户访问数据库(您的方法也是如此).如果不是这样,那么max(n)1方法将不是一个好方法.
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。