Trie樹的詳解及應用
來源:程序員人生 發(fā)布時間:2015-01-21 08:28:39 閱讀次數(shù):3508次
Trie樹,又稱單詞查找樹或鍵樹,是1種樹形結構,是1種哈希樹的變種。典型利用是用于統(tǒng)計和排序大量的字符串(但不但限于字符串),所以常常被搜索引擎系統(tǒng)用于文本詞頻統(tǒng)計。它的優(yōu)點是:最大限度地減少無謂的字符串比較,查詢效力比哈希表高。Trie的核心思想是空間換時間。利用字符串的公共前綴來下降查詢時間的開消以到達提高效力的目的。
Trie 的強大的地方就在于它的時間復雜度。它的插入和查詢時間復雜度都為 O(k) ,其中 k 為 key 的長度,與
Trie 中保存了多少個元素無關。Hash 表號稱是 O(1) 的,但在計算 hash 的時候就肯定會是 O(k) ,而且還有碰撞之類的問題;Trie 的缺點是空間消耗很高。
Trie樹特性:
1)根節(jié)點不包括字符,除根節(jié)點外每個節(jié)點都只包括1個字符。
2)從根節(jié)點到某1節(jié)點,路徑上經(jīng)過的字符連接起來,為該節(jié)點對應的字符串。
3)每一個節(jié)點的所有子節(jié)點包括的字符都不相同。
4)如果字符的種數(shù)為n,則每一個結點的出度為n,這也是空間換時間的體現(xiàn),浪費了很多的空間。
5)插入查找的復雜度為O(n),n為字符串長度。
基本思想(以字母樹為例):
1、插入進程
對1個單詞,從根開始,沿著單詞的各個字母所對應的樹中的節(jié)點分支向下走,直到單詞遍歷完,將最后的節(jié)點標記為紅色,表示該單詞已插入Trie樹。
2、查詢進程
一樣的,從根開始依照單詞的字母順序向下遍歷trie樹,1旦發(fā)現(xiàn)某個節(jié)點標記不存在或單詞遍歷完成而最后的節(jié)點未標記為紅色,則表示該單詞不存在,若最后的節(jié)點標記為紅色,表示該單詞存在。
字典樹的數(shù)據(jù)結構:
利用串構建1個字典樹,這個字典樹保存了串的公共前綴信息,因此可以下降查詢操作的復雜度。
下面以英文單詞構建的字典樹為例,這棵Trie樹中每一個結點包括26個孩子結點,由于總共有26個英文字母(假定單詞都是小寫字母組成)。
則可聲明包括Trie樹的結點信息的結構體:
-
typedef struct Trie_node
-
{
-
int count;
-
struct Trie_node* next[26];
-
bool exist;
-
}TrieNode , *Trie;
其中next是1個指針數(shù)組,寄存著指向各個孩子結點的指針。
如給出字符串"abc","ab","bd","dda",根據(jù)該字符串序列構建1棵Trie樹。則構建的樹以下:
Trie樹的根結點不包括任何信息,第1個字符串為"abc",第1個字母為'a',因此根結點中數(shù)組next下標為'a'⑼7的值不為NULL,其他同理,構建的Trie樹如圖所示,紅色結點表示在該處可以構成1個單詞。很明顯,如果要查找單詞"abc"是不是存在,查找長度則為O(len),len為要查找的字符串的長度。而若采取1般的逐一匹配查找,則查找長度為O(len*n),n為字符串的個數(shù)。明顯基于Trie樹的查找效力要高很多。
如上圖中:Trie樹中存在的就是abc、ab、bd、dda4個單詞。在實際的問題中可以將標記色彩的標志位改成數(shù)量count等其他符合題目要求的變量。
已知n個由小寫字母構成的平均長度為10的單詞,判斷其中是不是存在某個串為另外一個串的前綴子串。
下面對照3種方法:
1、 最容易想到的:即從字符串集中從頭往后搜,看每一個字符串是不是為字符串集中某個字符串的前綴,復雜度為O(n^2)。
2、 使用hash:我們用hash存下所有字符串的所有的前綴子串。建立存有子串hash的復雜度為O(n*len)。查詢的復雜度為O(n)* O(1)= O(n)。
3、 使用Trie:由于當查詢如字符串abc是不是為某個字符串的前綴時,明顯以b、c、d....等不是以a開頭的字符串就不用查找了,這樣迅速縮小查找的范圍和提高查找的針對性。所以建立Trie的復雜度為O(n*len),而建立+查詢在trie中是可以同時履行的,建立的進程也就能夠成為查詢的進程,hash就不能實現(xiàn)這個功能。所以總的復雜度為O(n*len),實際查詢的復雜度只是O(len)。
Trie樹的操作
在Trie樹中主要有3個操作,插入、查找和刪除。1般情況下Trie樹中很少存在刪除單獨某個結點的情況,因此只斟酌刪除整棵樹。
1、插入
假定存在字符串str,Trie樹的根結點為root。i=0,p=root。
1)取str[i],判斷p->next[str[i]⑼7]是不是為空,若為空,則建立結點temp,并將p->next[str[i]⑼7]指向temp,然后p指向temp;
若不為空,則p=p->next[str[i]⑼7];
2)i++,繼續(xù)取str[i],循環(huán)1)中的操作,直到遇到結束符'
主站蜘蛛池模板:
国产色网站
|
看av网站
|
男女精品视频
|
成年在线视频
|
欧美成人一区二区三区片免费
|
嫩草导航
|
欧美中文字幕一区二区三区
|
综合色婷婷一区二区亚洲欧美国产
|
九九视频在线
|
日韩电影一区二区三区
|
成人午夜免费毛片
|
亚洲国产精品久久
|
国产伦精品一区二区三区免
|
九九精品在线视频
|
中文字幕不卡视频
|
国产精品一区在线
|
亚洲成人18
|
国产一区色
|
欧美高清在线一区
|
日韩视频在线一区
|
国产乱国产乱300精品
|
国产搞黄色|
国产四区|
99精品成人|
精品久久久久久亚洲精品
|
欧美 日韩 国产 在线
|
91精品国产综合久久久久蜜臀
|
99精品视频免费在线观看
|
国产欧美日韩一区
|
欧美精品黑人猛交高潮
|
午夜精品久久久久久久久久久久
|
97在线免费观看视频
|
亚洲女人天堂成人av在线
|
91久久久久久久久久久久久
|
免费淫片|
99久久精品免费看国产一区二区三区
|
四虎884aa成人精品最新
|
成人免费在线播放
|
日韩精品久久
|
成人91|
亚洲午夜在线视频
|