Oracle包含Apostrope搜索

时间:2018-12-13 10:37:11

标签: oracle oracle11g

我正在使用Oracle 11g,并且有一个名为test的表,其中包含列firstnamelastname

  1. firstname列包含D'Arch
  2. Lastname列包含O'Neil

并且我有结合了firstnamelastname列的索引,并且正在使用CONTAINS (firstname, '%'|| 'D''A' ||'%') >0

Oracle Query是

select * 
from test 
where CONTAINS (firstname, '%'|| 'D''Ar' ||'%') >0

但是结果集为空。 Oracle Likeinstr关键字工作正常,但是我不想更改现有的实现。

关于这个问题的任何建议。

1 个答案:

答案 0 :(得分:1)

假设这些样本数据-请参阅下面的CTAS语句来创建它们。

FIRSTNAME LASTNAME
--------- --------
D'Arch    O'Neil   
DArch     ONeil    
D Arch    O Neil   
D.Arch    O.Neil 

要保留撇号,必须将其定义为printjoin字符。否则,它将在标记化过程中删除(与最后一行中的点比较)。

BEGIN
  ctxsys.ctx_ddl.create_preference('lex', 'BASIC_LEXER');
  ctxsys.ctx_ddl.set_attribute('lex', 'printjoins', '''');  
END;
/
---
BEGIN
  ctxsys.ctx_ddl.create_preference('pref', 'MULTI_COLUMN_DATASTORE');
  ctx_ddl.set_attribute('pref', 'columns', 'firstname, lastname');
END;
/

create index idx_test on test(firstname)
indextype is CTXSYS.CONTEXT
parameters ('datastore  pref LEXER  lex')
;

在创建索引后查看结果代码的最佳方法是查询$I表,该表包含所有代码:

select TOKEN_TEXT from DR$IDX_TEST$I;

TOKEN_TEXT                                                     
----------------------------------------------------------------
ARCH                                                             
D'ARCH                                                           
DARCH                                                            
FIRSTNAME                                                        
LASTNAME                                                         
NEIL                                                             
O                                                                
O'NEIL                                                           
ONEIL                                                            

如预期的那样,点消失了,但是撇号得以幸存。

现在,您可以查询并获得预期的结果:

select * 
from test 
where CONTAINS (firstname, '%D''Ar%') >0;

FIRSTNAME LASTNAME
--------- --------
D'Arch    O'Neil 

当然,当您使用MULTI_COLUMN_DATASTORE时,您也可以查询lastname列中的数据。

select * 
from test 
where CONTAINS (firstname, '%O''Ne%') >0;

FIRSTNAME LASTNAME
--------- --------
D'Arch    O'Neil

样本数据

create table test as
select 'D''Arch' firstname, 'O''Neil' Lastname from dual union all
select 'DArch' firstname, 'ONeil' Lastname from dual union all
select 'D Arch' firstname, 'O Neil' Lastname from dual union all
select 'D.Arch' firstname, 'O.Neil' Lastname from dual;