我试图找出一个字符串中是否存在字符串并将其解压缩。我使用了instr()
函数,但这可以作为LIKE函数:如果存在部分或整个单词,则返回它。
在这里,我希望得到字符串'Services',但是如果我将'Services'更改为'Service',它仍然有效。我不希望这样。如果输入“服务”,则应返回null而不是“服务”
修改:
我在这里要做的是缩写公司名称的某些部分。
这就是我的数据库表:
Word | Abb
---------+-----
Company | com
Limited | ltd
Service | serv
Services | servs
以下是代码:
Declare
Cursor Words Is
SELECT word,abb
FROM abbWords
processingWord VARCHAR2(50);
abbreviatedName VARCHAR(120);
fullName = 'A.D Company Services Limited';
BEGIN
FOR eachWord IN Words LOOP
--find the position of the word in name
wordPosition := INSTR(fullName, eachWord.word);
--extracts the word form the full name that matches the database
processingWord := Substr(fullName,instr(fullName,eachWord.word), length(eachWord.word));
--only process words that exist in name
if wordPosition > 0 then
abbreviatedName = replace(fullName, eachWord.word,eachWord.abb);
end if;
END lOOP;
END;
因此,如果用户输入“服务”,我不希望返回“服务”。我的意思是,如果找不到“服务”这个词而不是返回“服务”这个词的位置,那么单词位置应为0
答案 0 :(得分:4)
一种方法:
DECODE(INSTR('A.D Company Seervices Limited','Services'),
0,
NULL,
SUBSTR('A.D Company Services Limited',
INSTR('A.D Company Services Limited','Services'),
length('Services')))
如果找不到文本, INSTR()
将返回0。 DECODE()
将评估第一个参数,与第二个参数进行比较,如果匹配,则返回第三个参数,如果不匹配,则返回第四个参数。 (sqlfiddle link)
可能不是最优雅的方式,但符合您的要求。
答案 1 :(得分:3)
我认为你过于复杂了。您可以使用regular expressions执行所有操作。例如;如下表所示:
create table names ( name varchar2(100));
insert into names values ('A.D Company Services Limited');
insert into names values ('A.D Company Service Limited');
此查询仅返回名称'A.D Company Services Limited'
。
select *
from names
where regexp_like( name
, '(^|[[:space:]])services($|[[:space:]])'
, 'i' )
这意味着匹配字符串的开头^
,或者后跟服务的空格,后跟字符串末尾$
或空格。这就是正则表达式与使用instr
等区别的原因。您可以轻松地根据其他因素制作匹配。
然而,虽然这似乎是你的问题,但我认为这不是你想要做的。您尝试替换宽字符串中的字符串'serv'
,而不替换'services'
或'service'
。为此,您需要使用regexp_replace()
。
如果我将以下行添加到表中:
insert into names values ('A.D Company Serv Limited');
并运行此查询:
select regexp_replace( name
, '(^|[[:space:]])serv($|[[:space:]])'
, ' Services '
, 1, 0, 'i' )
from names
仅将更改的内容为' Serv '
,在此最新行中,将替换为' Services '
。注意空格;因为您不想将'Services'
替换为'ServServices'
,所以这些非常重要。
答案 2 :(得分:2)
INSTR
返回一个数字:匹配字符串第一次出现的索引。您应该使用regexp_substr
代替(10g +):
SQL> select regexp_substr('A.D Company Services Limited', 'Services') match,
2 regexp_substr('A.D Company Service Limited', 'Services') unmatch
3 from dual;
MATCH UNMATCH
-------- -------
Services
答案 3 :(得分:2)
另一种选择是使用类似的东西:
select replace(name,' serv ', ' Services ')
from names;
这将只取代位于2个空格之间的“Serv”字样。
谢谢你, 亚历克斯。