介绍完Oracle全文索引的BASIC_LEXER属性,这篇介绍Oracle中文语法属性CHINESE_LEXER和CHINESE_VGRAM_LEXER。
Oracle全文索引的BASIC属性主要是针对西方英语语系,英语语系的单词是通过空格、标点和回车来分隔的。而中文则需要索引来自动切词。[@more@]2 看下面这个例子:
SQL> CREATE TABLE T (ID NUMBER, DOCS VARCHAR2(1000));
表已创建。
SQL> INSERT INTO T VALUES (1, '一个中文例子,测试BASIC_LEXER语法属性是否可以正常识别中文。');
已创建 1 行。
SQL> COMMIT;
提交完成。
SQL> CREATE INDEX IND_T_DOCS ON T (DOCS) INDEXTYPE IS CTXSYS.CONTEXT;
索引已创建。
SQL> SELECT * FROM T WHERE CONTAINS(DOCS, '中文') > 0;
未选定行
SQL> SELECT * FROM T WHERE CONTAINS(DOCS, '一个中文例子') > 0;
ID DOCS
---------- ------------------------------------------------------------
1 一个中文例子,测试BASIC_LEXER语法属性是否可以正常识别中文。
通过BASIC_LEXER来索引中文,Oracle只识别被空格、标点和回车符分隔出来的部分。需要对中文内容进行索引的话,就必须使用中文的LEXER。
Oracle提供了两种预定义的中文LEXER属性:CHINESE_VGRAM_LEXER和CHINESE_LEXER。Oracle在文档上是这样描述的:
CHINESE_LEXER相对应CHINESE_VGRAM_LEXER属性有如下的优点:
产生的索引更小;
更好的查询响应时间;
产生更接近真实的索引切词,使得查询精度更高;
支持停用词。
虽然Oracle说明了使用CHINESE_LEXER的大量好处,但是CHINESE_LEXER的实际效果却存在一定的问题:
SQL> DROP INDEX IND_T_DOCS;
索引已丢弃。
SQL> TRUNCATE TABLE T;
表已截掉。
SQL> INSERT INTO T VALUES (1, '北京大学未名湖');
已创建 1 行。
SQL> INSERT INTO T VALUES (2, '北京邮电大学');
已创建 1 行。
SQL> INSERT INTO T VALUES (3, '北京市第十四中学');
已创建 1 行。
SQL> COMMIT;
提交完成。
SQL> CONN CTXSYS/CTXSYS@YANGTK
已连接。
SQL> BEGIN
2 CTX_DDL.CREATE_PREFERENCE('TEST_CHINESE_VGRAM_LEXER', 'CHINESE_VGRAM_LEXER');
3 CTX_DDL.CREATE_PREFERENCE('TEST_CHINESE_LEXER', 'CHINESE_LEXER');
4 END;
5 /
PL/SQL 过程已成功完成。
SQL> CONN YANGTK/YANGTK@YANGTK
已连接。
SQL> CREATE INDEX IND_T_DOCS ON T(DOCS) INDEXTYPE IS CTXSYS.CONTEXT
2 PARAMETERS ('LEXER CTXSYS.TEST_CHINESE_VGRAM_LEXER');
索引已创建。
SQL> SELECT * FROM T WHERE CONTAINS(DOCS, '北京') > 0;
ID DOCS
---------- ------------------------------------------------------------
3 北京市第十四中学
2 北京邮电大学
1 北京大学未名湖
SQL> DROP INDEX IND_T_DOCS;
索引已丢弃。
SQL> CREATE INDEX IND_T_DOCS ON T(DOCS) INDEXTYPE IS CTXSYS.CONTEXT
2 PARAMETERS ('LEXER CTXSYS.TEST_CHINESE_LEXER');
索引已创建。
SQL> SELECT * FROM T WHERE CONTAINS(DOCS, '北京') > 0;
ID DOCS
---------- ------------------------------------------------------------
2 北京邮电大学
通过对比结果可以发现:使用CHINESE_LEXER 没有将第一条记录和第三条记录中的北京检索出来。也许Oracle的CHINESE_LEXER认为北京大学和北京市是一个完整的词汇,而没有对其进行进 一步切分。也许这就是Oracle提到的这种切分方式更接近于真实的情况。我不知道读者会怎样看待这个问题,不过我更倾向于使用 CHINESE_VGRAM_LEXER,个人感觉返回记录多一些总比漏掉一些要好。
来自 “ ITPUB博客 ” ,链接:http://blog.itpub.net/271283/viewspace-1022231/,如需转载,请注明出处,否则将追究法律责任。
转载于:http://blog.itpub.net/271283/viewspace-1022231/