【問題描述】
在進行文法分析的時候,通常需要檢測乙個單詞是否在我們的單詞列表裡。為了提高查詢和定位的速度,通常都畫出與單詞列表所對應的單詞查詢樹,其特點如下:
1.根結點不包含字母,除根結點外每乙個結點都僅包含乙個大寫英文本母;
2.從根結點到某一結點,路徑上經過的字母依次連起來所構成的字母序列,稱為該結點對應的單詞。單詞列表中的每個單詞,都是該單詞查詢樹某個結點所對應的單詞;
3.在滿足上述條件下,該單詞查詢樹的結點數最少。
4.例如圖左邊的單詞列表就對應於右邊的單詞查詢樹。注意,對乙個確定的單詞列表,請統計對應的單詞查詢樹的結點數(包含根結點)。
【問題輸入】
輸入檔名為word.in,該檔案為乙個單詞列表,每一行僅包含乙個單詞和乙個換行/回車符。每個單詞僅由大寫的英文本母組成,長度不超過63個字母 。檔案總長度不超過32k,至少有一行資料。
【問題輸出】
輸出檔名為word.out,該檔案中僅包含乙個整數,該整數為單詞列表對應的單詞查詢樹的結點數。
【樣例輸入】aan
aspas
ascascii
basbasic
【樣例輸出】
首先要對建樹的過程有乙個了解。對於當前被處理的單詞和當前樹:在根結點的子結點中找單詞的第一位字母,若存在則進而在該結點的子結點中尋找第二位……如此下去直到單詞結束,即不需要在該樹中新增結點;或單詞的第n位不能被找到,即將單詞的第n位及其後的字母依次加入單詞查詢樹中去。但,本問題只是問你結點總數,而非建樹方案,且有32k檔案,所以應該考慮能不能不通過建樹就直接算出結點數?為了說明問題的本質,我們給出乙個定義:乙個單詞相對於另乙個單詞的差:設單詞1的長度為l,且與單詞2從第n位開始不一致,則說單詞1相對於單詞2的差為l-n+1,這是描述單詞相似程度的量。可見,將乙個單詞加入單詞樹的時候,須加入的結點數等於該單詞樹中已有單詞的差的最小值。
單詞的字典順序排列後的序列則具有類似的特性,即在乙個字典順序序列中,第m個單詞相對於第m-1個單詞的差必定是它對於前m-1個單詞的差中最小的。於是,得出建樹的等效演算法:
①讀入檔案;
②對單詞列表進行字典順序排序;
③依次計算每個單詞對前一單詞的差,並把差累加起來。注意:第 乙個單詞相對於「空」的差為該單詞的長度;
④累加和再加上1(根結點),輸出結果。
就給定的樣例,按照這個演算法求結點數的過程如下表:
先確定32k(32*1024=32768位元組)的檔案最多有多少單詞和字母。當然應該盡可能地存放較短的單詞。因為單詞不重複,所以長度為1的單詞(單個字母)最多26個;長
度為2的單詞最多為26*26=676個;因為每個單詞後都要乙個換行符(換行符在計算機中佔2個位元組),所以總共已經占用的空間為:(1+2)*26+(2+2)*676=2782位元組;
剩餘位元組(32768-2782=29986位元組)分配給長度為3的單詞(長度為3的單詞最多有26*26*26=17576個)有29986/(3+2)≈5997。所以單詞數量最多為
26+676+5997=6699。
定義乙個陣列:string a[32768];把所有單詞連續存放起來,用選擇排序或快排對單詞進行排序。
先排序,然後找相鄰兩個單詞的差值,再進行累加。
#include#includeusing namespace std;
int i,j,n,t,k;
string s;
string a[80001];//陣列可以達到32768 32k=32*1024=32768
int main()
} }
t=a[1].length();//第乙個單詞的長度
for(i=2;i<=n;i++)
//n--;
sort(a+1,a+n+1);
// for(int i=1;i<=n;i++) cout<
Trie 字首樹 字典樹 單詞查詢樹(資料結構)
在寫完了kmp演算法的部落格之後,我下定決心,一定要寫出一篇關於 ac自動機的部落格 ac自動機實際上就是字典樹上的kmp演算法。所以,考慮到廣大同學不一定會寫trie樹,特此在此處寫了一篇文章介紹介紹這種資料結構。字典樹 又稱單詞查詢樹,trie樹,是一種樹形結構,是一種雜湊樹的變種。典型應用是用...
資料結構 Trie(單詞查詢樹,字典樹,字首樹)
trie,又稱字首樹或字典樹,是一種有序樹,用於儲存關聯陣列,其中的鍵通常是字串。與二叉查詢樹不同,鍵不是直接儲存在節點中,而是由節點在樹中的位置決定。乙個節點的所有子孫都有相同的字首,也就是這個節點對應的字串,而根節點對應空字串。一般情況下,不是所有的節點都有對應的值,只有葉子節點和部分內部節點所...
資料結構之單詞詞典 B樹
詞典即索引,就是將乙個關鍵字與它對應的記錄相關聯的過程。是典型的根據屬性查詢記錄。在進行過程中可以進行編號壓縮,比如 114 116 119 可以記錄為114 2 3 二叉排序樹 左子樹上的所有結點的值小於它的根節點的值。二叉排序樹的作用主要是提高查詢和刪除關鍵字的效率。當要刪除某個關鍵字時,找到它...