精华内容
下载资源
问答
  • 今天小编就为大家分享一篇python正向最大匹配分词和逆向最大匹配分词的实例,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧
  • 前向最大匹配算法、后向最大匹配算法、jieba分词,使用python,完整的代码和运行结果
  • 中文分词应用很广泛,网上也有很多开源项目,下面这篇文章主要给大家介绍了关于java中文分词之正向最大匹配法的相关资料,文中通过示例代码介绍的非常详细,需要的朋友可以参考借鉴,下面随着小编来一起学习学习吧。
  • 主要介绍了python实现机械分词之逆向最大匹配算法代码示例,具有一定借鉴价值,需要的朋友可以参考下。
  • python正向最大匹配分词和逆向最大匹配分词完整的源代码分享,运行使用后对相关技术人员很有分享价值,为开发人员节省开发时间和提高开发思路是很不错的选择
  • python 双向最大匹配算法 双向最大匹配算法 双向最大匹配算法
  • 给定一个二分图和二分图中的任一匹配,通过最大匹配算法,确定该匹配是否是最大匹配并输出最大匹配的边集。最大匹配:M是一个二分图边集的子集,当M中任意两个边在顶点处不相交时,成M为二分图的一个匹配,最大匹配...
  • 二分图最大匹配算法

    2015-01-28 14:54:43
    二分图指的是这样一种图,其所有顶点可以分成两个集合X和Y,其中X或Y中任意两个在同一集合中的点都不相连,所有的边关联在两个顶点中,恰好一个属于集合X,另一个属于集合...图中包含边数最多的匹配称为图的最大匹配
  • MM算法有三种:一种正向最大匹配,一种逆向最大匹配和双向匹配。本程序实现了正向最大匹配算法。 本程序还可以从我的github上面下载:https://github.com/Zehua-Zeng/Maximum-Matching-Algorithm
  • 最大匹配法:最大匹配是指以词典为依据,取词典中最长单词为第一个次取字数量的扫描串,在词典中进行扫描(为提升扫描效率,还可以跟据字数多少设计多个字典,然后根据字数分别从不同字典中进行扫描)。 文档整理...

    编译原理实验二:Python实现中文分词–正向最大匹配和逆向最大匹配
    最大匹配法:最大匹配是指以词典为依据,取词典中最长单词为第一个次取字数量的扫描串,在词典中进行扫描(为提升扫描效率,还可以跟据字数多少设计多个字典,然后根据字数分别从不同字典中进行扫描)。
    在这里插入图片描述
    文档整理如下:
    在这里插入图片描述
    最大正向匹配代码如下:

    # -*- coding: utf-8 -*-
    """
    Created on Fri Feb 21 16:25:22 2020
    
    @author: lenovo
    """
    
    import numpy as np
    
    #处理词典库获得列表
    def get_dic():
        f=open("F:/学习文件/编译原理/实验二/词典文档.txt",'r')
        file_open=f.read().split()#按照空格处理文件
        f.close()
        chars=list(set(file_open))#去重之后获得列表
        return chars
    dic=get_dic()
    
    def readfile():
        max_length=0
        for i in dic:
            max_length=max(max_length,len(i))##获得最大长度
        zz=max_length
        f=open("F:/学习文件/编译原理/实验二/测试文档.txt",'r')
        ff=open("F:/学习文件/编译原理/实验二/生成文档.txt",'w')
        lines=f.readlines()
        f.close()
        for line in lines:#分别对每一行进行正向最大匹配处理
            max_length=zz
            my_list=[]
            len_hang=len(line)
            while len_hang>0:
                tryW=line[0:max_length]##切割字符串
                while tryW not in dic:
                    if len(tryW)==1:#长度为1的时候就直接退出
                        break;
                    tryW=tryW[0:len(tryW)-1]
                my_list.append(tryW)
                line=line[len(tryW):]
                len_hang=len(line)
            for i in my_list:
                ff.write(i+" ")
        ff.close()
    readfile()
    

    结果如下:
    在这里插入图片描述
    逆向最大匹配代码如下:

    # -*- coding: utf-8 -*-
    """
    Created on Fri Feb 21 19:04:54 2020
    
    @author: lenovo
    """
    
    import numpy as np
    
    #处理词典库获得列表
    def get_dic():
        f=open("F:/学习文件/编译原理/实验二/词典文档.txt",'r')
        file_open=f.read().split()
        f.close()
        chars=list(set(file_open))
        return chars
    dic=get_dic()
    
    def readfile():
        max_length=0
        for i in dic:
            max_length=max(max_length,len(i))##获得最大长度
        zz=max_length
        f=open("F:/学习文件/编译原理/实验二/测试文档.txt",'r')
        ff=open("F:/学习文件/编译原理/实验二/生成文档逆向最大匹配.txt",'w')
        lines=f.readlines()
        f.close()
        for line in lines:#分别对每一行进行逆向最大匹配处理
            max_length=zz
            my_list=[]
            len_hang=len(line)
            while len_hang>0:
                tryW=line[max(0,len_hang-max_length):len_hang]#防止溢出
                while tryW not in dic:
                    if len(tryW)==1:
                        break;
                    tryW=tryW[1:len(tryW)]#这里注意,一直是从1开始的
                my_list.append(tryW)
                line=line[0:len_hang-len(tryW)]
                len_hang=len(line)
        while len(my_list):
            tt=my_list.pop()#这里类似栈的操作
            ff.write(tt+" ")
        ff.close()
    readfile()##012345
    

    结果如下:
    在这里插入图片描述
    逆向需要考虑一些下标的变化,防止溢出。
    努力加油a啊,(o)/~

    展开全文
  • MM算法有三种:一种正向最大匹配,一种逆向最大匹配和双向匹配。本程序实现了反向最大匹配算法。 本程序还可以从我的github上面下载:https://github.com/Zehua-Zeng/Reverse-Maximum-Matching-Algorithm
  • 计算一般无向图中的最大加权匹配。 可以选择只考虑最大基数匹配。... 一些想法来自斯坦福大学博士 HJ Gabow 的“非二部图上最大匹配算法的实现”。 论文,1973。 Ed Rothberg 的最大重量匹配 AC 程序被广
  • Java实现分词(正向最大匹配和逆向最大匹配)两种方法实现
  • 最大匹配算法

    2017-04-09 17:32:13
    最大匹配算法,中文分词
  • 用Java编写的一般图的最大匹配算法,可以正常运行;并且附有设计文档及运行结果图。
  • 正向(前向)最大匹配与逆向(后向)最大匹配。 所谓词典正向最大匹配就是将一段字符串进行分隔,其中分隔 的长度有限制,然后将分隔的子字符串与字典中的词进行匹配,如果匹配成功则进行下一轮匹配,直到所有字符...

    正向(前向)最大匹配与逆向(后向)最大匹配。

            中文分词目前可以分为“规则分词”,“统计分词”,“混合分词(规则+统计)”这三个主要流派。这次介绍下基于规则的分词,其是一种机械的分词方法,主要通过维护词典,在切分语句时,将语句的每个字符串与词表中的词逐一进行匹配,找到则切分,否则不予切分。

            正向最大匹配算法:这里需要知道两点,一个是分词词典(也即是已经分词过的词典),另一个是需要被分词的文档。假定分词词典中的最长词有ii个汉子字符串,则用被处理文档的当前字符串中的前ii个字作为匹配字段,查找字典。若此时分词词典中存在这样一个字符串,则匹配成功,而此时被匹配的字段切分出来。如果匹配失败,将匹配字段中的最后一个字去掉,对此时剩下的字串重新与分词词典进行匹配,如此下去直到匹配成功。也即是切分出一个词或剩余字串的长度为零为止,这个时候才是匹配了一轮,接着进行下一个ii字字串的匹配,方法同上,直到文档被扫描完为止。

    示例说明

    示例1:

    对字符串:“研究生命的起源”进行分词。
    假定我们的字典中的相关内容如下:
    研究
    研究生
    生命


    起源


    假定最大匹配字数设定为5。


    正向最大匹配过程

    研究生命的
    研究生命
    研究生 #第一个词匹配成功
    命的起源
    命的起
    命的
    命 #第二个词匹配成功,一个单字
    的起源
    的起
    的 #第三个词匹配成功
    起源 #第四个词匹配成功
    那么正向最大匹配的结果就是
    研究生 命 的 起源


    逆向最大匹配的过程

    生命的起源
    命的起源
    的起源
    起源 #第一个词匹配成功
    研究生命的
    究生命的
    生命的
    命的
    的 #第二个词匹配成功
    研究生命
    究生命
    生命 #第三个词匹配成功
    研究 #第四个词匹配成功
    所以逆向最大匹配后的结果为
    研究 生命 的 起源
    两种分词过程总结
    【正向匹配:从左到右,逐步去掉右部(底部)的字进行新一轮匹配,逆向匹配:从右到左,逐步去掉左部(底部)的字进行新一轮匹配】
    因为中文比较复杂以及中文的特殊性,逆向最大匹配大多时候往往会比正向要准确。

    示例2:

    对“我们在野生动物园玩”进行分词。

    1、正向最大匹配法:

    正向即从前往后取词,从7->1,每次减一个字,直到词典命中或剩下1个单字。

    第1次:“我们在野生动物”,扫描7字词典,无

    第2次:“我们在野生动”,扫描6字词典,无

    。。。。

    第6次:“我们”,扫描2字词典,有

    扫描中止,输出第1个词为“我们”,去除第1个词后开始第2轮扫描,即:

    第2轮扫描:

    第1次:“在野生动物园玩”,扫描7字词典,无

    第2次:“在野生动物园”,扫描6字词典,无

    。。。。

    第6次:“在野”,扫描2字词典,有

    扫描中止,输出第2个词为“在野”,去除第2个词后开始第3轮扫描,即:

    第3轮扫描:

    第1次:“生动物园玩”,扫描5字词典,无

    第2次:“生动物园”,扫描4字词典,无

    第3次:“生动物”,扫描3字词典,无

    第4次:“生动”,扫描2字词典,有

    扫描中止,输出第3个词为“生动”,第4轮扫描,即:

    第4轮扫描:

    第1次:“物园玩”,扫描3字词典,无

    第2次:“物园”,扫描2字词典,无

    第3次:“物”,扫描1字词典,无

    扫描中止,输出第4个词为“物”,非字典词数加1,开始第5轮扫描,即:

    第5轮扫描:

    第1次:“园玩”,扫描2字词典,无

    第2次:“园”,扫描1字词典,有

    扫描中止,输出第5个词为“园”,单字字典词数加1,开始第6轮扫描,即:

    第6轮扫描:

    第1次:“玩”,扫描1字字典词,有

    扫描中止,输出第6个词为“玩”,单字字典词数加1,整体扫描结束。

    正向最大匹配法,最终切分结果为:“我们/在野/生动/物/园/玩”,其中,单字字典词为2,非词典词为1。

    2、逆向最大匹配法:

    逆向即从后往前取词,其他逻辑和正向相同。即:

    第1轮扫描:“在野生动物园玩”

    第1次:“在野生动物园玩”,扫描7字词典,无

    第2次:“野生动物园玩”,扫描6字词典,无

    。。。。

    第7次:“玩”,扫描1字词典,有

    扫描中止,输出“玩”,单字字典词加1,开始第2轮扫描

    第2轮扫描:“们在野生动物园”

    第1次:“们在野生动物园”,扫描7字词典,无

    第2次:“在野生动物园”,扫描6字词典,无

    第3次:“野生动物园”,扫描5字词典,有

    扫描中止,输出“野生动物园”,开始第3轮扫描

    第3轮扫描:“我们在”

    第1次:“我们在”,扫描3字词典,无

    第2次:“们在”,扫描2字词典,无

    第3次:“在”,扫描1字词典,有

    扫描中止,输出“在”,单字字典词加1,开始第4轮扫描

    第4轮扫描:“我们”

    第1次:“我们”,扫描2字词典,有

    扫描中止,输出“我们”,整体扫描结束。

    逆向最大匹配法,最终切分结果为:“我们/在/野生动物园/玩”,其中,单字字典词为2,非词典词为0。

    3、双向最大匹配法:

    正向最大匹配法和逆向最大匹配法,都有其局限性,我举得例子是正向最大匹配法局限性的例子,逆向也同样存在(如:长春药店,逆向切分为“长/春药店”),因此有人又提出了双向最大匹配法,双向最大匹配法。即,两种算法都切一遍,然后根据大颗粒度词越多越好,非词典词和单字词越少越好的原则,选取其中一种分词结果输出。

    如:“我们在野生动物园玩”

    正向最大匹配法,最终切分结果为:“我们/在野/生动/物/园/玩”,其中,两字词3个,单字字典词为2,非词典词为1。

    逆向最大匹配法,最终切分结果为:“我们/在/野生动物园/玩”,其中,五字词1个,两字词1个,单字字典词为2,非词典词为0。

    非字典词:正向(1)>逆向(0)(越少越好)

    单字字典词:正向(2)=逆向(2)(越少越好)

    总词数:正向(6)>逆向(4)(越少越好)

    因此最终输出为逆向结果。

     

    代码

    [中文分词之正向最大匹配算法]

    from: https://youzipi.blog.csdn.net/article/details/105525351

    ref:

     

    展开全文
  • 最大匹配法分词Python

    2013-03-26 11:21:03
    最大匹配法分词Python,文档,代码齐全。注释齐全。输入为人民日报标准语料库。10分绝对不亏。
  • 中文分词一直都是中文自然语言处理领域的基础研究。目前,网络上流行的很多中文分词软件都可以在付出较少的代价的同时...MM算法有三种:一种正向最大匹配,一种逆向最大匹配和双向匹配。本程序实现了正向最大匹配算法。
  • 按照匹配方法来划分,主要有正向最大匹配、逆向最大匹配以及双向最大匹配。 1. 正向最大匹配 正向最大匹配(Maximum Match,MM): 从左向右取待切分汉语句的m个字符作为匹配字段,m为机器词典中最长词条的字符数。...

    基于规则的分词是一种机械分词方法,需要不断维护和更新词典,在切分语句时,将语句的每个字符串与词表中的每个次进行逐一匹配,找到则切分,找不到则不予切分。

    按照匹配方法来划分,主要有正向最大匹配、逆向最大匹配以及双向最大匹配。

    1. 正向最大匹配

    正向最大匹配(Maximum Match,MM):

    1. 从左向右取待切分汉语句的m个字符作为匹配字段,m为机器词典中最长词条的字符数。
    2. 查找机器词典并进行匹配。若匹配成功,则将这个匹配字段作为一个词切分出来。 若匹配不成功,则将这个匹配字段的最后一个字去掉,剩下的字符串作为新的匹配字段,进行再次匹配,重复以上过程,直到切分出所有词为止。

    比如我们现在有个词典,最长词的长度为5,词典中存在“南京市长”“长江大桥”和 “大桥”3个词。现采用正向最大匹配对句子“南京市长江大桥”进行分词,那么首先从句 子中取出前5个字“南京市长江”,发现词典中没有该词,于是缩小长度,取前4个字“南 京市长”,词典中存在该词,于是该词被确认切分。再将剩下的“江大桥”按照同样方式 切分,得到“江”“大桥”,最终分为“南京市长”“江”“大桥”3个词。显然,这种结果不是我们所希望的。

    正向最大匹配法示例代码如下:

    class MaximumMatch:
        """正向最大匹配的中文分词器"""
        def __init__(self):
            self.window_size = 3  # 字典中最长词条的字符数
    
        def cut(self, text):
            global piece
            result = []
            index = 0  # 前指针
            text_length = len(text)
            dictionary = {'研究', '研究生', '声明', '起源'}
            while text_length > index:
                for r_index in range(self.window_size+index, index, -1):  # 后指针
                    piece = text[index: r_index]
                    if piece in dictionary:
                        index = r_index - 1
                        break
    
                index = index + 1
                result.append(piece)
            return result
    
    
    if __name__ == '__main__':
        text = '研究生命的起源'
        tokenizer = MaximumMatch()
        print(tokenizer.cut(text))
    

    输出结果:

    ['研究生', '命', '的', '起源']
    

    2. 逆向最大匹配

    逆向最大匹配简称为RMM法。RMM法的基本原理与MM法大致相同,不同的是分词切分的方向与MM法相反。

    逆向最大匹配法从被处理文档的末端开始匹配扫描,每次取最末端的m个字符(m为词典中最长词数作为匹配字段,若匹配失败,则去掉匹配字段最前面的一个字,继续匹配。相应地,它使用的分词词典是逆序词典,其中的每个词条都将按逆序方式存放。在实际处理时,先将文档进行倒排处理,生成逆序文档。然后,根据逆序词典,对逆序文档用正向最大匹配法处理即可。

    由于汉语中偏正结构较多,若从后向前匹配,可以适当提高精确度。所以,逆向最大匹配法比正向最大匹配法的误差要小。统计结果表明,单纯使用正向最大匹配的错误率为1/169,单纯使用逆向最大匹配的错误率为1/25。比如之前的“南京市长江大桥”,按照逆向最大匹配,最终得到“南京市”“长江大桥”的分词结果。当然,如此切分并不代表完全正确、可能有个叫“江大桥”的“南京市长”也说不定。

    逆向最大匹配法示例代码如下:

    class ReverseMaximumMatch:
        """逆向最大匹配"""
        def __init__(self):
            self.window_size = 3
    
        def cut(self, text):
            result = []
            right = len(text)  # 右指针
            dic = {'研究', '研究生', '生命', '命', '的', '起源'}
            global piece
            while right > 0:
                for left in range(right - self.window_size, right):  # 固定右指针,左指针逐渐右移
                    piece = text[left: right]  # 切片
                    if piece in dic:  # 当命中时
                        right = left + 1  # 命中更新
                        break
                right = right - 1  # 自然更新
                result.append(piece)
            result.reverse()
            return result
    
    if __name__ == '__main__':
        text = '研究生命的起源'
        rmm_tokenizer = ReverseMaximumMatch()
        print(rmm_tokenizer.cut(text))
    

    输出结果:

    ['研究', '生命', '的', '起源']
    

    3. 双向最大匹配

    双向最大匹配法是将正向最大匹配法得到的分词结果和逆向最大匹配法得到的结果进行比较,然后按照最大匹配原则,选取词数切分最少的作为结果。据SunM.s.和 Benjamin K…研究表明,对于中文中90.0%左右的句子,正向最大匹配和逆向最大匹配的切分结果完全重合且正确,只有大概9.0%的句子采用两种切分方法得到的结果不一样,但其中必有一个是正确的(歧义检测成功),只有不到1.0%的句子,或者正向最大匹配和逆向最大匹配的切分结果虽重合却都是错的,或者正向最大匹配和逆向最大匹配的切分结果不同但两个都不对(歧义检测失败)。这正是双向最大匹配法在实用中文信息处理系统中得以广泛使用的原因所在。

    前面列举的“南京市长江大桥”采用双向最大匹配法进行切分,中间产生“南京市/江/大桥”和“南京市/长江大桥”两种结果,最终选取词数较少的“南京市/长江大桥”这一结果。

    双向最大匹配的规则如下所示:

    1. 如果正反向分词结果词数不同,则取分词数量较少的那个结果(上例:“南京市江/大桥”的分词数量为3,而“南京市/长江大桥”的分词数量为2,所以返回分词数量为2的结果)
    2. 如果分词结果词数相同,则:
      ① 分词结果相同,就说明没有歧义,可返回任意一个结果。
      ② 分词结果不同,返回其中单字较少的那个。比如前文示例代码中,正向最大匹配返回的结果为“[‘研究生’,‘命’,‘的起源’]”,其中单字个数为2个;而逆向最大匹配返回的结果为“[研究’,生命’, ‘的’,‘起源’]",其中单字个数为1。所以返回的是逆向最大匹配的结果。

    代码如下:

    class BidirectionalMaximumMatch:
        """双向最大匹配"""
        def _count_single_char(self, world_list: List[str]):
            """
            统计单字成词的个数
            """
            return sum(1 for word in world_list if len(word) == 1)
    
        def cut(self, text: str):
            mm = MaximumMatch()
            rmm = ReverseMaximumMatch()
            f = mm.cut(text)
            b = rmm.cut(text)
            if len(f) < len(b):
                return f
            elif len(f) > len(b):
                return b
            else:
                return b if self._count_single_char(f) >= self._count_single_char(b) else f
    
    if __name__ == '__main__':
        text = '研究生命的起源'
        bmm = BidirectionalMaximumMatch()
        print(bmm.cut(text))
    

    输出结果:

    ['研究', '生命', '的', '起源']
    

    基于规则的分词一般都较为简单高效,但是词典的维护面临很庞大的工作量。在网络发达的今天,网络新词层出不穷,很难通过词典覆盖所有词。另外,词典分词也无法区分歧义以及无法召回新词。


    在实际项目中,我们是否会考虑使用规则分词?
    虽然使用规则分词的分词准确率看上去非常高,但是规则分词有几个特别大的问题:
    ① 不断维护词典是非常烦琐的,新词总是层出不穷,人工维护费时费力;
    ② 随着词典中条目数的增加,执行效率变得越来越低;
    ③ 无法解决歧义问题。
    所以在这里不建议采用规则分词法。

    展开全文
  • 在一个已经语料库的基础上,进行词频统计,然后根据统计的词用正向和反向最大匹配算法进行中文分词。
  • 主要介绍了Java实现的最大匹配分词算法,简单说明了最大匹配分词算法的原理并结合具体实例形式最大匹配分词算法的实现方法与相关注意事项,需要的朋友可以参考下
  • 用C#开发的基于正向和逆向最大匹配的分词程序。
  • 正向最大匹配算法:从左到右将待分词文本中的几个连续字符与词表匹配,如果匹配上,则切分出一个词,并且要做到最大匹配。 反向最大匹配算法:从右到左将待分词文本中的几个连续字符与词表匹配,如果匹配上,则切分...

    正向最大匹配算法:从左到右将待分词文本中的几个连续字符与词表匹配,如果匹配上,则切分出一个词,并且要做到最大匹配。
    反向最大匹配算法:从右到左将待分词文本中的几个连续字符与词表匹配,如果匹配上,则切分出一个词,并且要做到最大匹配。
    这份代码对正向最大匹配算法和反向最大匹配算法进行封装,需要在代码的目录下存放一份词典,词典取名为:chineseDic.txt。
    样例如下:

    ,nr
    劼人,nr
    勍,nr
    喆,nr
    揳入,v
    

    即可以是无headers的csv格式文件,词,词性这样的格式存放。
    代码如下:

    #!/usr/bin/python3
    # -*- coding:utf-8 -*-
    # Author:ChenYuan
    import time
    import os
    
    
    class CSegment(object):
        
        def __init__(self):
            self.question = None
            self.true_index = []
            self.with_user_dict = False
            self.reverse = False
            self.result_reverse = False
            self.MM_result_index = []
            self.RMM_result_index = []
            self.MM_result_list = []
            self.RMM_result_list = []
            self.word_pos_dict = {}
    
        def read_user_dict(self, dict_path):
            """
            :param dict_path: 用户定义的词典文件
            :return:
            """
            tic = time.clock()
            word_pos = {}
            if not os.path.exists(dict_path):
                print('该文件不存在')
                assert os.path.exists(dict_path) is True
            with open(dict_path, 'r')as fp:
                for line in fp:
                    line = line.strip()
                    word = line.split(',')[0]
                    pos = line.split(',')[1]
                    word_pos[word] = pos
            self.word_pos_dict = word_pos
            self.with_user_dict = True
            toc = time.clock()
            time_clock = toc - tic
            print('\033[1;31;47m')
            print('*' * 50)
            print('*Load user dict:\t', dict_path)
            print('*Load time:\t', time_clock)
            print('*' * 50)
            print('\033[0m')
    
        def read_true_sentence(self, true_result):
            """
            :param true_result: 正确的分词结果
            :return: 分词结果的下表元组列表
            """
            if len(true_result) == 0:
                return []
            else:
                true_list = [t.strip() for t in true_result.split('/')]
                true_index = []
                index = 0
                for t in true_list:
                    lth = len(t)
                    if index + lth == len(self.question):
                        break
                    if self.question[index:index + lth] == t:
                        true_index.append(str((index, index + lth)))
                        index += lth
                return true_index
    
        def get_true_index(self, result_list):
            """
            :param result_list: 结果列表
            :return: 结果对应的下表列表
            """
            if self.reverse:
                self.reverse = False
                return self.RMM_result_index
            else:
                return self.MM_result_index
    
        def evaluate(self, true_list, result_list):
            """
            :param true_list: 正确的分词列表
            :param result_list: 算法得到的分词列表
            :return: 三种评价指标:{正确率,召回率,F1-score}
            """
            true_index = self.read_true_sentence(true_list)
            result_index = self.get_true_index(result_list)
            if len(true_index) == 0:
                print('未导入正确结果,不能进行评估')
                assert len(true_index) > 0
            tp = 0
            fp = 0
            fn = 0
            for r, t in zip(result_index, true_index):
                if r in true_index:
                    tp += 1
                if r not in true_index:
                    fp += 1
                if t not in result_index:
                    fn += 1
            precision = tp / (tp + fp)
            recall = tp / (tp + fn)
            F1 = 2 * precision * recall / (precision + recall)
            evaluate_result = {'Precision': precision, 'Recall': recall, 'F1': F1}
    
            return evaluate_result
    
        @staticmethod
        def read_own_dict():
            dict_path = './chineseDic.txt'
            word_pos_dict = {}
            if not os.path.exists(dict_path):
                print('该文件不存在')
                assert os.path.exists(dict_path) is True
    
            with open(dict_path, 'r')as fp:
                for line in fp:
                    line = line.strip()
                    word = line.split(',')[0]
                    w_pos = line.split(',')[1]
                    word_pos_dict[word] = w_pos
    
            return word_pos_dict
    
        def MM(self, sentence, lth, pos=False):
            """
            :param sentence: 待分词句子
            :param lth: 正向匹配的最大长度
            :param pos: 结果是否显示词性标注
            """
            self.reverse = False
            self.result_reverse = False
            if lth <= 1:
                print('max_len 不能小于2')
                assert lth > 1
            if len(sentence) == 0:
                print('原句子不能为空')
                assert len(sentence) > 0
            self.question = sentence
            if self.with_user_dict:
                word_pos_dict = self.word_pos_dict
            else:
    
                word_pos_dict = self.read_own_dict()
    
            result_list = []
            result_index = []
            max_lth = lth
            index = 0
            index_last = index + max_lth
            while index <= len(sentence):
                if sentence[index:index_last] in word_pos_dict.keys():
                    if pos:
                        result_list.append(sentence[index:index_last] + '/' + word_pos_dict[sentence[index:index_last]])
                    else:
                        result_list.append(sentence[index:index_last])
                    result_index.append(str((index, index_last)))
                    index = index_last
                    index_last = index + max_lth
                else:
                    index_last -= 1
    
            self.MM_result_index = result_index
            self.MM_result_list = result_list
    
        def RMM(self, sentence, lth, pos=False):
            """
            :param sentence: 待分词句子
            :param lth: 反向匹配的最大长度
            :param pos: 结果是否显示词性标注
            :return:
            """
            self.reverse = True
            self.result_reverse = True
            if lth <= 1:
                print('max_len 不能小于2')
                assert lth > 1
            if len(sentence) == 0:
                print('原句子不能为空')
                assert len(sentence) > 0
            self.question = sentence
            if self.with_user_dict:
                word_pos_dict = self.word_pos_dict
            else:
                word_pos_dict = self.read_own_dict()
    
            result_list = []
            result_index = []
            max_lth = lth
            index_last = len(sentence)
            index = index_last - max_lth
            while index_last != 0:
                if sentence[index:index_last] in word_pos_dict.keys():
                    if pos:
                        result_list.append(sentence[index:index_last] + '/' + word_pos_dict[sentence[index:index_last]])
                    else:
                        result_list.append(sentence[index:index_last])
                    result_index.append(str((index, index_last)))
                    index_last = index
                    index = index_last - max_lth
                else:
                    index += 1
            result_list.reverse()
            result_index.reverse()
            self.RMM_result_index = result_index
            self.RMM_result_list = result_list
    
        def get_result(self):
            """
            :return: 返回结果
            """
            if self.result_reverse:
                return self.RMM_result_list
            else:
                return self.MM_result_list
    

    由于是课程作业,对方法的调用和定义的变量有要求,所以显得比较笨拙,但是代码简单,可修改性强,没有很复杂的函数调用和第三方模块调用。
    下面是测试方法:

    question = '命名时应考虑的因素:直观、时髦用语、暗示创业模型、有说服力、能吸引顾客的注意力。'
    true = '命名/  时/  应/  考虑/  的/  因素/  :/  直观/  、/  时髦/  用语/  、/  暗示/  创业/  模型/  、/  有/  说服力/  、/  能/  吸引/  顾客/  的/  注意力/  。/  '
    # 这里是指用户词典
    chinese_dict = 'chineseDic.txt'
    max_len = 3
    # 实例化一个对象cut
    cut = CSegment()
    # 加载用户词典
    cut.read_user_dict(chinese_dict)
    # 正向最大匹配
    cut.MM(sentence=question, lth=max_len, pos=True)
    # 获取结果
    MM_result = cut.get_result()
    print(MM_result)
    # 评价分词结果,需要有true(正确答案)
    evaluate = cut.evaluate(true, MM_result)
    print(evaluate)
    # 反向最大匹配
    cut.RMM(sentence=question, lth=max_len, pos=True)
    RMM_result = cut.get_result()
    print(RMM_result)
    evaluate = cut.evaluate(true, RMM_result)
    print(evaluate)
    
    展开全文
  • 最大匹配Matlab代码

    2013-08-27 16:41:25
    最大匹配算法KM算法的maltab实现。其实当数据较少时,用lingo很快就能解出来。
  • 正向最大匹配法 &逆向最大匹配法 原理对比 下面介绍的分词算法中最简单的正向最大匹配和反向最大匹配。 这种两种方法都是机械分词方法,它是按照一定的策略将待分析的汉字串与一个”充分大的”机器词典中的...
  • python前向逆向最大匹配分词

    热门讨论 2012-07-04 14:30:21
    基于词典的前向逆向最大匹配分词,词典自己生成,用utf8文本文件存储即可
  • 最新逆向最大匹配分词算法 盘古分词 分词算法 中文分词 源码

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 626,103
精华内容 250,441
关键字:

最大匹配