`
iluoxuan
  • 浏览: 580027 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

中文分词原理--正向最大匹配

    博客分类:
  • java
 
阅读更多

转载原文:http://hxraid.iteye.com/blog/667134 

 

中文分词一直都是中文自然语言处理领域的基础研究。目前,网络上流行的很多中文分词软件都可以在付出较少的代价的同时,具备较高的正确率。而且不少中文分词软件支持Lucene扩展。但不管实现如何,目前而言的分词系统绝大多数都是基于中文词典的匹配算法。

 

在这里我想介绍一下中文分词的一个最基础算法:最大匹配算法 (Maximum Matching,以下简称MM算法) 。MM算法有两种:一种正向最大匹配,一种逆向最大匹配。

 

● 算法思想

 

正向最大匹配算法:从左到右将待分词文本中的几个连续字符与词表匹配,如果匹配上,则切分出一个词。但这里有一个问题:要做到最大匹配,并不是第一次匹配到就可以切分的 。我们来举个例子:

           待分词文本:   content[]={"中","华","民","族","从","此","站","起","来","了","。"}

           词表:   dict[]={"中华", "中华民族" , "从此","站起来"}

(1) 从content[1]开始,当扫描到content[2]的时候,发现"中华"已经在词表dict[]中了。但还不能切分出来,因为我们不知道后面的词语能不能组成更长的词(最大匹配)。

(2) 继续扫描content[3],发现"中华民"并不是dict[]中的词。但是我们还不能确定是否前面找到的"中华"已经是最大的词了。因为"中华民"是dict[2]的前缀。

(3) 扫描content[4],发现"中华民族"是dict[]中的词。继续扫描下去:

(4) 当扫描content[5]的时候,发现"中华民族从"并不是词表中的词,也不是词的前缀。因此可以切分出前面最大的词——"中华民族"。

 

由此可见,最大匹配出的词必须保证下一个扫描不是词表中的词或词的前缀才可以结束。

 

 

● 算法实现

 

词表的内存表示: 很显然,匹配过程中是需要找词前缀的,因此我们不能将词表简单的存储为Hash结构。在这里我们考虑一种高效的字符串前缀处理结构——Trie树《Trie Tree 串集合查找 》。这种结构使得查找每一个词的时间复杂度为O(word.length),而且可以很方便的判断是否匹配成功或匹配到了字符串的前缀。

 

下图是我们建立的Trie结构词典的部分,(词语例子:"中华","中华名族","中间","感召","感召力","感受")。

           

(1) 每个结点都是词语中的一个汉字。

(2) 结点中的指针指向了该汉字在某一个词中的下一个汉字。这些指针存放在以汉字为key的hash结构中。

(3) 结点中的"#"表示当前结点中的汉字是从根结点到该汉字结点所组成的词的最后一个字。

 

TrieNode源代码如下:

Java代码  收藏代码
  1. import java.util.HashMap;  
  2. /** 
  3.  * 构建内存词典的Trie树结点 
  4.  *  
  5.  * @author single(宋乐) 
  6.  * @version 1.01, 10/11/2009 
  7.  */  
  8. public class TrieNode {  
  9.   
  10.     /**结点关键字,其值为中文词中的一个字*/  
  11.     public char key=(char)0;  
  12.     /**如果该字在词语的末尾,则bound=true*/  
  13.     public boolean bound=false;  
  14.     /**指向下一个结点的指针结构,用来存放当前字在词中的下一个字的位置*/  
  15.     public HashMap<Character,TrieNode> childs=new HashMap<Character,TrieNode>();  
  16.       
  17.     public TrieNode(){  
  18.     }  
  19.       
  20.     public TrieNode(char k){  
  21.         this.key=k;  
  22.     }  
  23. }  

 

这套分词代码的优点是:

(1) 分词效率高。纯内存分词速度大约240.6ms/M,算上IO读取时间平均1.6s/M。测试环境:Pentium(R)  4 CPU  3.06GHZ、1G内存。

(2) 传统的最大匹配算法需要实现确定一个切分的最大长度maxLen。如果maxLen过大,则大大影响分词效率。而且超过maxLen的词语将无法分出来。但本算法不需要设置maxLen。只要词表中有的词,不管多长,都能够切分。

(3) 对非汉字的未登录词具备一定的切分能力。比如英文单词[happy, steven],产品型号[Nokia-7320],网址[http://www.sina.com]等。

 

缺点也很明显:

(1) 暂时无词性标注功能,对中文汉字的未登录词无法识别,比如某个人名。

(2) 内存占用稍大,目前词表为86725个词。如果继续扩展词表,很有可能内存Trie树将非常庞大。

 

代码的进一步优化方案:

(1) 想在内存占用空间上降低代价。实际上Trie树主要的空间消耗在每个结点的指针HashMap上。我使用的是JDK中的HashMap,其加载因子为 loadFactor= 0.75,初始化空间大小为DEFAULT_INITIAL_CAPACITY= 16。每次存储数据量超过 loadFactor* DEFAULT_INITIAL_CAPACITY的时候,整个Map空间将翻倍。 因此会照成一定的空间浪费。

 

      但目前还没有想到很好的办法,即能够随机定位到下一个结点的指针,又降低Hash结构的空间代价?

 

 

下面是我实现的基于Trie词典结构的正向最大匹配算法的源代码包和分词词表,可供大家学习下载。但绝对不允许任何商业性质的传播,违者必究。

分享到:
评论

相关推荐

    分词匹配算法:正向最大匹配和反向最大匹配

    正向最大匹配是机械分词方法中的一种,它的工作原理是从左到右扫描汉字串,从左到右扫描,找到最长的匹配词语。例如,在字符串“今天来了许多新同事”中,从左到右扫描,会得到如下结果: * 今天来了 * 来了许多新 ...

    中文分词-正向最大匹配法和逆向最大匹配法的实现

    总的来说,中文分词是NLP的重要一环,而正向和逆向最大匹配法是基础的分词策略。掌握这些方法有助于理解自然语言处理的底层逻辑,同时在没有现成工具可用的情况下,也可以快速构建自己的分词系统。

    正向最大匹配算法实现中文分词

    MM算法有三种:一种正向最大匹配,一种逆向最大匹配和双向匹配。本程序实现了正向最大匹配算法。 本程序还可以从我的github上面下载:https://github.com/Zehua-Zeng/Maximum-Matching-Algorithm

    一个简单的分词系统(可以选择正向最大匹配分词或逆向最大匹配)

    在这个简单的分词系统中,提供了两种主要的分词算法:正向最大匹配(Forward Maximum Matching, FMM)和逆向最大匹配(Backward Maximum Matching, BMM)。下面我们将详细探讨这两种方法及其应用。 首先,正向最大...

    matlab中文分词——最大正向匹配法.rar

    本项目以"matlab中文分词——最大正向匹配法.rar"为主题,重点讨论了如何在MATLAB环境中实现最大正向匹配算法进行中文分词。 MATLAB是一种广泛使用的数学计算和编程环境,其强大的数值计算和可视化功能使其成为科研...

    Java实现分词(正向最大匹配和逆向最大匹配)两种方法实现

    本文介绍了Java环境下实现中文分词的两种常用算法:正向最大匹配法和逆向最大匹配法。这两种方法各有优缺点,在实际应用中可以根据具体需求选择合适的分词策略。此外,通过加载词典和设置最大匹配长度等方式,可以...

    改进的正向最大匹配分词算法

    在这个过程中,我们可以将正向最大匹配分词算法的原理应用于以下几个方面: 1. **版本信息的比较**:可以将版本号视为一段文本,利用分词算法快速准确地比较客户端和服务器端的版本信息差异。 2. **数据传输的...

    C++编写中文分词最大匹配的分词源码

    本篇文章将深入探讨如何使用C++实现中文分词的“最大匹配”算法,并通过源码分析来帮助学习者理解其工作原理。 “最大匹配”(Maximal Matching,简称MM)是一种常见的中文分词算法,它的核心思想是从待分词的句子...

    采用正向逆向最大匹配才实现汉字分词wordppl.rar

    总之,"采用正向逆向最大匹配才实现汉字分词wordppl.rar"是一个学习和研究汉字分词的好资源,通过它,你可以掌握分词的基本方法,理解正向和逆向最大匹配的优缺点,并探索如何将两者有效结合,以应对实际应用场景中...

    正向匹配分词实例及详解

    正向最大匹配法是一种常用的中文分词方法,它的核心思想是从左到右的方向,按最大可能的长度依次切分出尽可能多的词汇。具体步骤如下: 1. **确定最大词长**:首先确定词典中的最长词条长度。 2. **匹配过程**: -...

    中文分词原理.pdf

    ### 中文分词原理及其在搜索引擎中的应用 #### 一、搜索引擎工作原理 搜索引擎的工作流程主要包括三个阶段:爬行抓取网页、首次处理以及排名。 1. **爬行抓取网页**:搜索引擎通过释放大量的爬虫程序(俗称“蜘蛛...

    一种基于改进最大匹配快速中文分词算法

    ### 基于改进最大匹配快速中文分词算法的知识点 #### 一、中文分词技术概述 中文分词作为自然语言处理中的基础步骤,在文本分析、机器翻译、信息检索等多个领域发挥着至关重要的作用。它主要负责将连续的中文字符...

    最新逆向最大匹配分词算法 盘古分词 分词算法 中文分词 源码

    在提供的压缩包文件中,包含了各种与分词相关的源码,例如"zt_逆向最大匹配分词算法"可能是实现逆向最大匹配算法的具体代码,"秒盘古分词"可能是指快速版本的盘古分词程序,"中文分词"和"英文分词"源码分别针对中文...

    中文正向最大匹配

    中文正向最大匹配(Maximal Matching,简称MM)是一种在自然语言处理中广泛使用的分词方法,主要用于将连续的汉字序列切分成具有语义意义的词语。这种方法在处理中文文本时,通过查找最大可能的词汇来进行分词,有助...

    python正向最大匹配分词和逆向最大匹配分词的实例

    逆向最大匹配分词算法和正向最大匹配分词算法在原理上是类似的,只不过匹配的方向相反。 文章给出的逆向最大匹配分词的Python实现代码同样分为字符编码转换函数、逆向最大匹配函数以及主函数三个部分。 字符编码...

    正向最大匹配分词算法及KNN文本分类算法python实现.zip

    正向最大匹配分词算法(Forward Maximum Matching, FMM)是自然语言处理(NLP)领域中常用的一种中文分词方法。它的工作原理是从待分词的文本的起始位置开始,每次尝试匹配尽可能长的词语,直到文本末尾。在匹配过程...

    java 正向匹配算法分析

    正向最大匹配算法(FMM,Forward Maximum Matching)是中文分词中最常见的方法之一,尤其在早期的分词系统中应用广泛。本文将详细解析Java实现的正向最大匹配算法,通过代码示例深入理解其工作原理。 #### 正向最大...

    最大正向逆向分词算法

    最大正向逆向分词算法结合了最大正向匹配和逆向最大匹配两种策略,以提高分词的准确率和效率。最大正向匹配是从句子的开始位置,选取最长的词典中的词作为分词结果,直到无法找到更长的词为止。逆向最大匹配则从句子...

    python基础编程:python中文分词教程之前向最大正向匹配算法详解

    下面这篇文章主要给大家介绍了关于python中文分词教程之前向最大正向匹配算法的相关资料,需要的朋友可以参考下。 前言 大家都知道,英文的分词由于单词间是以空格进行分隔的,所以分词要相对的容易些,而中文就不同...

Global site tag (gtag.js) - Google Analytics