日本不卡不码高清免费观看,久久国产精品久久w女人spa,黄色aa久久,三上悠亚国产精品一区二区三区

您的位置:首頁技術(shù)文章
文章詳情頁

淺析Python實現(xiàn)DFA算法

瀏覽:255日期:2022-06-15 17:06:07
目錄一、概述二、匹配關(guān)鍵詞三、算法實現(xiàn)3.1、構(gòu)建存儲結(jié)構(gòu)3.2、匹配關(guān)鍵詞3.3、完整代碼四、其他用法4.1、添加通配符一、概述

計算機操作系統(tǒng)中的進程狀態(tài)與切換可以作為 DFA 算法的一種近似理解。如下圖所示,其中橢圓表示狀態(tài),狀態(tài)之間的連線表示事件,進程的狀態(tài)以及事件都是可確定的,且都可以窮舉。

淺析Python實現(xiàn)DFA算法

DFA 算法具有多種應(yīng)用,在此先介紹在匹配關(guān)鍵詞領(lǐng)域的應(yīng)用。

二、匹配關(guān)鍵詞

我們可以將每個文本片段作為狀態(tài),例如“匹配關(guān)鍵詞”可拆分為“匹”、“匹配”、“匹配關(guān)”、“匹配關(guān)鍵”和“匹配關(guān)鍵詞”五個文本片段。

淺析Python實現(xiàn)DFA算法

【過程】:

初始狀態(tài)為空,當(dāng)觸發(fā)事件“匹”時轉(zhuǎn)換到狀態(tài)“匹”; 觸發(fā)事件“配”,轉(zhuǎn)換到狀態(tài)“匹配”; 依次類推,直到轉(zhuǎn)換為最后一個狀態(tài)“匹配關(guān)鍵詞”。

再讓我們考慮多個關(guān)鍵詞的情況,例如“匹配算法”、“匹配關(guān)鍵詞”以及“信息抽取”。

淺析Python實現(xiàn)DFA算法

可以看到上圖的狀態(tài)圖類似樹形結(jié)構(gòu),也正是因為這個結(jié)構(gòu),使得 DFA 算法在關(guān)鍵詞匹配方面要快于關(guān)鍵詞迭代方法(for 循環(huán))。經(jīng)常刷 LeetCode 的讀者應(yīng)該清楚樹形結(jié)構(gòu)的時間復(fù)雜度要小于 for 循環(huán)的時間復(fù)雜度。

for 循環(huán):

keyword_list = []for keyword in ['匹配算法', '匹配關(guān)鍵詞', '信息抽取']: if keyword in 'DFA 算法匹配關(guān)鍵詞':keyword_list.append(keyword)

for 循環(huán)需要遍歷一遍關(guān)鍵詞表,隨著關(guān)鍵詞表的擴充,所需的時間也會越來越長。

DFA 算法:找到“匹”時,只會按照事件走向特定的序列,例如“匹配關(guān)鍵詞”,而不會走向“匹配算法”,因此遍歷的次數(shù)要小于 for 循環(huán)。具體的實現(xiàn)放在下文中。

【問】:那么如何構(gòu)建狀態(tài)圖所示的結(jié)構(gòu)呢?

【答】:在 Python 中我們可以使用 dict 數(shù)據(jù)結(jié)構(gòu)。

state_event_dict = { '匹': {'配': { '算': {'法': { 'is_end': True},'is_end': False }, '關(guān)': {'鍵': { '詞': {'is_end': True }, 'is_end': False},'is_end': False }, 'is_end': False},'is_end': False }, '信': {'息': { '抽': {'取': { 'is_end': True},'is_end': False }, 'is_end': False},'is_end': False }}

用嵌套字典來作為樹形結(jié)構(gòu),key 作為事件,通過 is_end 字段來判斷狀態(tài)是否為最后一個狀態(tài),如果是最后一個狀態(tài),則停止?fàn)顟B(tài)轉(zhuǎn)換,獲取匹配的關(guān)鍵詞。

【問】:如果關(guān)鍵詞存在包含關(guān)系,例如“匹配關(guān)鍵詞”和“匹配”,那么該如何處理呢?

【答】:我們?nèi)匀豢梢杂?is_end 字段來表示關(guān)鍵詞的結(jié)尾,同時添加一個新的字段,例如 is_continue 來表明仍可繼續(xù)進行匹配。除此之外,也可以通過尋找除 is_end 字段外是否還有其他的字段來判斷是否繼續(xù)進行匹配。例如下面代碼中的“配”,除了 is_end 字段外還有“關(guān)”,因此還需要繼續(xù)進行匹配。

state_event_dict = { '匹': {'配': { '關(guān)': {'鍵': { '詞': {'is_end': True }, 'is_end': False},'is_end': False }, 'is_end': True},'is_end': False }}

接下來,我們來實現(xiàn)這個算法。

三、算法實現(xiàn)

使用 Python 3.6 版本實現(xiàn),當(dāng)然 Python 3.X 都能運行。

3.1、構(gòu)建存儲結(jié)構(gòu)

def _generate_state_event_dict(keyword_list: list) -> dict: state_event_dict = {} # 遍歷每一個關(guān)鍵詞 for keyword in keyword_list:current_dict = state_event_dictlength = len(keyword)for index, char in enumerate(keyword): if char not in current_dict:next_dict = {'is_end': False}current_dict[char] = next_dictcurrent_dict = next_dict else:next_dict = current_dict[char]current_dict = next_dict if index == length - 1:current_dict['is_end'] = True return state_event_dict

關(guān)于上述代碼仍然有不少可迭代優(yōu)化的地方,例如先對關(guān)鍵詞列表按照字典序進行排序,這樣可以讓具有相同前綴的關(guān)鍵詞集中在一塊,從而在構(gòu)建存儲結(jié)構(gòu)時能夠減少遍歷的次數(shù)。

3.2、匹配關(guān)鍵詞

def match(state_event_dict: dict, content: str): match_list = [] state_list = [] temp_match_list = [] for char_pos, char in enumerate(content):# 首先找到匹配項的起點if char in state_event_dict: state_list.append(state_event_dict) temp_match_list.append({'start': char_pos,'match': '' })# 可能會同時滿足多個匹配項,因此遍歷這些匹配項for index, state in enumerate(state_list): if char in state:state_list[index] = state[char]temp_match_list[index]['match'] += char# 如果抵達匹配項的結(jié)尾,表明匹配關(guān)鍵詞完成if state[char]['is_end']: match_list.append(copy.deepcopy(temp_match_list[index])) # 如果還能繼續(xù),則繼續(xù)進行匹配 if len(state[char].keys()) == 1:state_list.pop(index)temp_match_list.pop(index) # 如果不滿足匹配項的要求,則將其移除 else:state_list.pop(index)temp_match_list.pop(index) return match_list3.3、完整代碼

import reimport copyclass DFA: def __init__(self, keyword_list: list):self.state_event_dict = self._generate_state_event_dict(keyword_list) def match(self, content: str):match_list = []state_list = []temp_match_list = []for char_pos, char in enumerate(content): if char in self.state_event_dict:state_list.append(self.state_event_dict)temp_match_list.append({ 'start': char_pos, 'match': ''}) for index, state in enumerate(state_list):if char in state: state_list[index] = state[char] temp_match_list[index]['match'] += char if state[char]['is_end']:match_list.append(copy.deepcopy(temp_match_list[index]))if len(state[char].keys()) == 1: state_list.pop(index) temp_match_list.pop(index)else: state_list.pop(index) temp_match_list.pop(index)return match_list @staticmethod def _generate_state_event_dict(keyword_list: list) -> dict:state_event_dict = {}for keyword in keyword_list: current_dict = state_event_dict length = len(keyword) for index, char in enumerate(keyword):if char not in current_dict: next_dict = {'is_end': False} current_dict[char] = next_dict current_dict = next_dictelse: next_dict = current_dict[char] current_dict = next_dictif index == length - 1: current_dict['is_end'] = Truereturn state_event_dictif __name__ == '__main__': dfa = DFA(['匹配關(guān)鍵詞', '匹配算法', '信息抽取', '匹配']) print(dfa.match('信息抽取之 DFA 算法匹配關(guān)鍵詞,匹配算法'))

輸出:

[

    {

        ’start’: 0, 

        ’match’: ’信息抽取’

    }, {

        ’start’: 12, 

        ’match’: ’匹配’

    }, {

        ’start’: 12, 

        ’match’: ’匹配關(guān)鍵詞’

    }, {

        ’start’: 18, 

        ’match’: ’匹配’

    }, {

        ’start’: 18,

        ’match’: ’匹配算法’

    }

]

四、其他用法4.1、添加通配符

在敏感詞識別時往往會遇到同一種類型的句式,例如“你這個傻X”,其中 X 可以有很多,難道我們需要一個個添加到關(guān)鍵詞表中嗎?最好能夠通過類似正則表達式的方法去進行識別。一個簡單的做法就是“*”,匹配任何內(nèi)容。

添加通配符只需要對匹配關(guān)鍵詞過程進行修改:

def match(self, content: str): match_list = [] state_list = [] temp_match_list = [] for char_pos, char in enumerate(content):if char in self.state_event_dict: state_list.append(self.state_event_dict) temp_match_list.append({'start': char_pos,'match': '' })for index, state in enumerate(state_list): is_find = False state_char = None # 如果是 * 則匹配所有內(nèi)容 if '*' in state:state_list[index] = state['*']state_char = state['*']is_find = True if char in state:state_list[index] = state[char]state_char = state[char]is_find = True if is_find:temp_match_list[index]['match'] += charif state_char['is_end']: match_list.append(copy.deepcopy(temp_match_list[index])) if len(state_char.keys()) == 1:state_list.pop(index)temp_match_list.pop(index) else:state_list.pop(index)temp_match_list.pop(index) return match_list

main() 函數(shù)。

if __name__ == '__main__': dfa = DFA(['匹配關(guān)鍵詞', '匹配算法', '信息*取', '匹配']) print(dfa.match('信息抽取之 DFA 算法匹配關(guān)鍵詞,匹配算法,信息抓取'))

輸出:

[

    {

        ’start’: 0, 

        ’match’: ’信息抽取’

    }, {

        ’start’: 12,

        ’match’: ’匹配’

    }, {

        ’start’: 12,

        ’match’: ’匹配關(guān)鍵詞’

    }, {

        ’start’: 18,

        ’match’: ’匹配’

    }, {

        ’start’: 18,

        ’match’: ’匹配算法’

    }, {

        ’start’: 23,

        ’match’: ’信息抓取’

    }

]

以上就是淺析Python實現(xiàn)DFA算法的詳細(xì)內(nèi)容,更多關(guān)于Python DFA算法的資料請關(guān)注好吧啦網(wǎng)其它相關(guān)文章!

標(biāo)簽: Python 編程
相關(guān)文章:
日本不卡不码高清免费观看,久久国产精品久久w女人spa,黄色aa久久,三上悠亚国产精品一区二区三区
日本va欧美va瓶| 欧美精品一区二区久久| 国产精品2023| 亚洲一区二区动漫| 97se综合| 欧美日韩网址| 亚洲日产国产精品| 狠狠爱www人成狠狠爱综合网| 国产videos久久| 久久av综合| 日本综合视频| 天堂av在线一区| 久久五月天小说| 欧美日韩精品免费观看视欧美高清免费大片| 国产欧美日韩在线观看视频| 一区二区三区四区在线观看国产日韩| 91精品啪在线观看国产18| 欧美精品影院| 一区二区三区网站| 男女男精品网站| 免费人成在线不卡| 麻豆亚洲精品| 蜜桃av一区二区| 亚洲精品人人| 久久狠狠久久| 麻豆久久久久久| 国产精品欧美日韩一区| 亚洲精选av| 国产一卡不卡| 精品九九在线| 性欧美xxxx免费岛国不卡电影| 九九色在线视频| 亚洲大全视频| 亚洲精品一级二级三级| 国产欧美69| 久久精品高清| 日韩在线a电影| 日韩精品a在线观看91| 国产精品白丝久久av网站| 欧美黄色一区二区| 韩国精品主播一区二区在线观看 | 午夜av不卡| 午夜亚洲福利在线老司机| 亚洲精品大全| 美女国产一区二区三区| 日韩国产网站| 视频一区中文字幕精品| 福利视频一区| 亚洲一区亚洲| 成人日韩av| 日本大胆欧美人术艺术动态| 欧美激情 亚洲a∨综合| 日韩黄色大片| 国产无遮挡裸体免费久久| 久久激情一区| 国产乱码精品一区二区亚洲| 欧美1区2区3区| 精品视频91| 91成人在线精品视频| 久久中文字幕二区| 嫩草伊人久久精品少妇av杨幂| 日韩视频中文| av在线资源| 国产九一精品| 亚洲ww精品| 99在线观看免费视频精品观看| 久久gogo国模啪啪裸体| 黄色亚洲精品| 老牛影视精品| 久久免费影院| 最新国产精品久久久| 黑丝一区二区三区| 久久蜜桃av| 群体交乱之放荡娇妻一区二区| 国产欧美大片| 国产亚洲一区| 国产精品久久久久9999高清| 免费一区二区视频| 亚洲综合另类| 国产一区日韩一区| 日韩一区二区三区免费| 青青青免费在线视频| 国产探花一区| 日韩国产欧美一区二区三区| 日韩一二三区在线观看| 久久一区二区三区电影| 国产成人免费| 午夜久久tv| 国产精品亚洲综合久久| 久久精品观看| 国产欧美高清视频在线| 久久精品动漫| 国产亚洲高清在线观看| 亚洲欧洲一区| 国产一区不卡| 日韩精品久久久久久| 日韩av一级| 日韩精品视频中文字幕| 日韩免费av| 国产精品亲子伦av一区二区三区| 性欧美69xoxoxoxo| 国产一区不卡| 91p九色成人| 日韩精品一级二级| 99视频精品全部免费在线视频| 国产精品一区二区免费福利视频| 夜夜嗨网站十八久久 | 久久国产精品色av免费看| 国产韩日影视精品| 亚洲国产成人二区| 鲁大师精品99久久久| 丝袜美腿亚洲一区二区图片| 日韩中文字幕高清在线观看| 国产精品videossex| 日韩欧美中文字幕电影| 亚洲欧美视频一区二区三区| 精品日韩毛片| 91精品一区二区三区综合| 国产精品毛片久久| 红杏一区二区三区| 精品精品久久| 色婷婷色综合| 日本а中文在线天堂| 中文av在线全新| 丁香六月综合| se01亚洲视频| 裤袜国产欧美精品一区| 国产 日韩 欧美 综合 一区 | 亚洲午夜久久久久久尤物| 黑人精品一区| 久久精品一区二区不卡| 亚洲福利免费| 狠狠色综合网| 亚洲丝袜美腿一区| 日韩精品一区二区三区中文在线| 日韩精品亚洲专区在线观看| 国产视频网站一区二区三区| 国产精品v一区二区三区| 欧美激情91| 精品国产亚洲一区二区三区| 日韩免费小视频| 先锋影音久久久| 欧美日韩18| 日韩电影免费在线观看| 欧洲激情综合| 日韩不卡一区二区三区| 久久免费精品| 九一精品国产| 欧美午夜三级| 日韩一区欧美| 亚洲日本在线观看视频| 精品一区91| 国产精品视区| 精品九九在线| 午夜在线一区二区| 成人在线免费观看网站| 亚洲少妇诱惑| 国产a亚洲精品| 亚洲精品伊人| 欧美成人a交片免费看| 亚洲日本欧美| 欧美高清不卡| 精品视频亚洲| 91亚洲精品视频在线观看| 欧美aa一级| 国产精品xxxav免费视频| 亚洲精品网址| 欧产日产国产精品视频| 久久国内精品视频| 欧美日韩一区二区综合 | 美女网站一区| 国产亚洲电影| 亚洲精选av| 99国产精品视频免费观看一公开| 精品视频在线你懂得| 日本aⅴ精品一区二区三区| 最新日韩欧美| 欧美成人久久| 欧美 日韩 国产一区二区在线视频 | 黄色成人精品网站| 日韩专区精品| av免费不卡国产观看| 开心激情综合| 美女在线视频一区| 日韩高清在线观看一区二区| 国产精品人人爽人人做我的可爱 | 国产精品综合| 国产伦精品一区二区三区千人斩 | 久久影视一区| 激情婷婷亚洲| 欧美a级一区| 亚洲女同一区| 老鸭窝亚洲一区二区三区| 国产亚洲综合精品| 亚洲一区二区三区高清| 亚洲自啪免费| 日韩精品1区2区3区| 国产麻豆精品久久| 国产一区二区三区日韩精品| 精品欧美视频|