现在的位置: 首页 > 综合 > 正文

说说MMSeg分词

2013年07月03日 ⁄ 综合 ⁄ 共 1936字 ⁄ 字号 评论关闭

记得06年的时候,我就学习过Lucene.Net一段时间,也写过一个分词。那个比较简单,就是一个最大逆向匹配加一个词库。不过,今年早些时候,硬盘坏了。所有数据都丢了。

上上周公司一个项目要用到搜索,我自然又想到了Lucene。并发现一个叫MMSeg的中文分词。据官方说法,正确率高达98%点多。

 

本人嘴拙,请大家看原文:http://www.solol.org/projects/mmseg/

 

不废话了:

其实MMSeg分词理解起来很容易,主要是chunk和四个规则。

chunk:

一个chunk就是一句话的一种分词方式。包括一个词条数组和四个属性。

打个比方:

“研究生命”用匹配的话,至少有两种:

研究/生命   VS      研究生/命

这就是两个chunk。

一个chunk有四个重要的属性:

长度:chunk中个词的长度之和,这里两个chunk的长度都是4.

代码如下:

 public int getLength() {
  if (length == -1) {
   length = 0;
   for (int i = 0; i < words.length; i++) {
    length += words[i].getLength();
   }
  }

  return length;
 }

平均长度:长度/词数.4/2=2

代码如下:

 public double getAverageLength() {
  if (averageLength == -1D) {
   averageLength = (double) getLength() / (double) words.length;
  }

  return averageLength;
 }

 

标准差平方:chunk中各个词条的长度减去平均长度的差的平方的和,再除以词条数目。唉,这句话说的真难懂啊。哈哈哈看代码:

public double getVariance() {
  if (variance == -1D) {
   double tempVariance = 0D;
   for (int i = 0; i < words.length; i++) {
    double temp = (double)words[i].getLength()-getAverageLength();
    tempVariance += temp * temp;
   }
   
   variance = Math.sqrt(tempVariance / (double) words.length);   
  }
  return variance;
 }

 

自由语素度:各单词条词频的对数之和。

看代码:

public double getDegreeOfMorphemicFreedom() {
  if (degreeMorphemicFreedom == -1D) {
   degreeMorphemicFreedom = 0D;
   for (int i = 0; i < words.length; i++) {
    if (words[i].getLength() == 1) {
     degreeMorphemicFreedom += Math.log((double) words[i].getFrequency());
    }
   }
  }
  return degreeMorphemicFreedom;
 }

 

最重要的chunk的概念理解了之后,就要理解四个规则了。

规则1:取最大匹配的chunk (Rule 1: Maximum matching)

这个规则好理解,就是取chunk长度最长的几个。注意是几个噢。

规则2:取平均词长最大的chunk (Rule 2: Largest average word length)

这个规则也好理解,就是取chunk平均长度最大的几个。

规则3:取词长标准差最小的chunk (Rule 3: Smallest variance of word lengths)

这个不说了,对应的属性是getVariance,取最小。

规则4:取单字词自由语素度之和最大的chunk (Rule 4: Largest sum of degree of morphemic freedom of one-character words)

这个一样,对应属性是getDegreeOfMorphemicFreedom,取最大。

 

如果经过这个四个规则的过滤,剩下的chunk数大于1,就这个分词就无能为力了。需要我们自己扩展了,其实扩展挺容易,再想出一个规则来就行了,哈哈哈。当然,自己扩展的规则,调用方法略微不一样点。

 

废话不多说:

java版代码:http://files.cnblogs.com/bqrm/mmseg-v0.3.zip

.net版:http://files.cnblogs.com/bqrm/mmseg-v0.1.net.zip

抱歉!评论已关闭.