IKAnalyzer结合Lucene实现中文分词

Posted funnyboy0128

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了IKAnalyzer结合Lucene实现中文分词相关的知识,希望对你有一定的参考价值。

1、基本介绍

  随着分词在信息检索领域应用的越来越广泛,分词这门技术对大家并不陌生。对于英文分词处理相对简单,经过拆分单词、排斥停止词、提取词干的过程基本就能实现英文分词,单对于中文分词而言,由于语义的复杂导致分词并没英文分词那么简单,一般都是通过相关的分词工具来实现,目前比较常用的有庖丁分词以及IKAnalyzer等。这里我们主要通过一个简单的Demo聊聊IKAnalyzer的基本使用。IKAnalyzer是一个开源的,基于java开发的分词工具包,它独立于Lucene项目,同时提供了Lucene的默认实现。

2、IKAnalyzer结合Lucene实现简单的中文分词

  我们通过一个基本的Demo来实践说明,步骤如下:

step1:准备相关的Jar依赖,lucene-core-5.1.0.jar、ik.jar,然后新建项目,引入相关依赖项目结构如下:

IkDemo-src

     -con.funnyboy.ik

                  -IKAnalyzer.cfg.xml

     -stopword.dic

                  -ext.dic

            -Reference Libraries

     -lucene-core-5.1.0.jar

     -ik.jar

IKAnalyzer.cfg.xml:配置扩展词典以及停止词典 内容如下:

<?xml version="1.0" encoding="UTF-8"?>

<!DOCTYPE properties SYSTEM "http://java.sun.com/dtd/properties.dtd"> 

<properties>   <comment>IK Analyzer 扩展配置</comment>

   <entry key="ext_dict">ext.dic;</entry>

   <entry key="ext_stopwords">stopword.dic;</entry>

</properties>

其中的ext.dic配置自己的扩展字典,stopword.dic配置自己的扩展停止词字典

step2:通过java代码验证测试

public class MyIkTest {

  public static String str = "中国人民银行我是中国人";

  public static void main(String[] args) {  

     MyIkTest test = new MyIkTest();  

     test.wordCount("", str);

   }

   private void wordCount(String arg,String content) {

       Analyzer analyzer = new IKAnalyzer(true); // IK实现分词  true:用最大词长分词  false:最细粒度切分   

    StringReader reader = null;   

    TokenStream ts = null;   try {        

      reader = new StringReader(content);    

      ts = analyzer.tokenStream(arg,reader);    

      CharTermAttribute term = ts.addAttribute(CharTermAttribute.class);   

      ts.reset();        

      Map<String, Integer> map = new HashMap<String, Integer>(); //统计    

      while (ts.incrementToken()) {     

        String str = term.toString();     

        Object o = map.get(str);     

        if (o == null) {      

          map.put(str, new Integer(1));   

         } else {      

          Integer i = new Integer(((Integer) o).intValue() + 1);     

           map.put(str, i);     

        }   

       }        

      List<Entry<String, Integer>> list = new ArrayList<Entry<String, Integer>>(map.entrySet());    

      Collections.sort(list,new Comparator<Map.Entry<String, Integer>>() {     

        public int compare(Map.Entry<String, Integer> o1,Map.Entry<String, Integer> o2) {      

          return (o2.getValue() - o1.getValue());     

        }    });         

       for (int k=0;k<list.size();k++) {     

        Entry<String, Integer> it=list.get(k);     

        String word = it.getKey().toString();     

        System.err.println(word+"["+it.getValue()+"]");    

       }           

    } catch (Exception e) {

       } finally {        

      if(reader != null){    

         reader.close();    

      }   

      if (analyzer != null) {     

        analyzer.close();    

      }  

     }  

   }

  }

执行程序测试结果如下:

中国人民银行[1]

中国人[1]

我[1]

3、配置说明

a、如何自定义配置扩展词典和停止词典    IKAnalyzer.cfg.xml中定义了扩展词典和停止词典,如果有多好个可以通过;配置多个。扩展词典是指用户可以根据自己定义的词义实现分词,比如人名在默认的词典中并未实现,需要自定义实现分词,卡可以通过在ext.dic中新增自定义的词语。停止词是指对于分词没有实际意义但出现频率很高的词,比如吗、乎等语气词,用户也可以通过在stopword.dic中自定义相关的停止词。

b、关于最大词长分词和最小粒度分词的区分    在IKAnalyzer构造方法中可以通过提供一个标示来实现最大词长分词和最小粒度分词,true为最大词长分词,默认是最小粒度分词。对"中国人民银行我是中国人"分别测试结果如下:

最大词长分词结果如下:

中国人民银行[1]

中国人[1]

我[1]

最小粒度分词结果如下:
国人[2]
中国人[2]
中国[2]
人民[1]
中国人民银行[1]
我[1]
人民银行[1]
中国人民[1]
银行[1]

 

以上是关于IKAnalyzer结合Lucene实现中文分词的主要内容,如果未能解决你的问题,请参考以下文章

IK 分词器和ElasticSearch集成使用

Elasticsearch安装ik中文分词插件

方便Lucene高版本使用IKAnalyzer分词包

中文分词工具哪个好用

Lucene使用IKAnalyzer分词实例 及 IKAnalyzer扩展词库

IK分词器应用