|
Grafy a tabuľky |
Knuth-Morris-Prathov algoritmus
|
Priemerné počty porovnaní vybraných implementácií |
//Knuth-Morris-Prattov algoritmus vyhladavania zadaneho vzoru "vzor" s poctom znakov "dlzka"
//funkcia vracia index prveho znaku najdeneho vzoru v retazci
//(v pripade neuspechu vyhladavania vracia -1)
int CRetazec::najdi_KMP(char* vzor, int dlzka){
if (dlzka > MAX_DLZKA_VZORU) return -2;
int postupnost[MAX_DLZKA_VZORU+1];
pre(vzor, dlzka, &postupnost[0]);
int i=0;
int j=0;
while (++p_a_porovnani_ && j < velkost_) {
if (++p_b_porovnani_ && vzor[i] == retazec_[j]) {
if (++p_b_porovnani_ && i == dlzka-1) {
return (j-dlzka+1);
//i=postupnost[i];
}
else {i++; j++;}
}
else if (++p_c_porovnani_ && postupnost[i] == -1) {i=0; j++;}
else i=postupnost[i];
}
return -1;
}
//funkcia na vytvorenie pomocneho pola pre KMP algoritmus
void CRetazec::pre(char* vzor, int dlzka, int* postupnost){
int i = 0;
int j = postupnost[0] = -1;
while (++p_d_porovnani_ && i < dlzka) {
while (++p_d_porovnani_ && j > -1 && ++p_d_porovnani_ && vzor[i] != vzor[j])
{ j = postupnost[j]; }
i++;
j++;
if (++p_d_porovnani_ && vzor[i] == vzor[j]) postupnost[i] = postupnost[j];
else postupnost[i] = j;
}
} |
Počet porovnaní, cyklov a času trvania algoritmu pre veľkosť abecedy=3 znaky, veľkosť vzoru=3 znaky. |
počet znakov v prehľadávanom reťazci |
p_a_porovnani_ |
p_b_porovnani_ |
p_c_porovnani_ |
p_d_porovnani_ |
čas |
10 |
13,00 |
15,00 |
9,000 |
14,00 |
0,2932 |
100 |
132,0 |
176,0 |
86,00 |
14,00 |
2,270 |
1.000 |
1324,0 |
1802,0 |
844,0 |
14,00 |
21,22 |
10.000 |
13282,0 |
17992,0 |
8570,0 |
14,00 |
211,7 |
100.000 |
133013,0 |
180636,0 |
85388,0 |
14,00 |
2129,0 |
|
Z nameraných hodnôt môžeme vidieť, že súčet a, b, c porovnaní je približne rovný 4-násobku dĺžky prehľadávaného reťazca. Porovnania d súvisia s vytváraním pomocnej tabuľky. |
|
Počet porovnaní, cyklov a času trvania algoritmu pre veľkosť abecedy=24 znakov, veľkosť vzoru=3 znaky. |
počet znakov v prehľadávanom reťazci |
p_a_porovnani_ |
p_b_porovnani_ |
p_c_porovnani_ |
p_d_porovnani_ |
čas |
10 |
12,00 |
12,00 |
10,00 |
14,00 |
0,2837 |
100 |
107,0 |
112,0 |
100,0 |
14,00 |
1,380 |
1.000 |
1042,0 |
1083,0 |
999,0 |
14,00 |
11,94 |
10.000 |
10405,0 |
10823,0 |
9985,0 |
14,00 |
118,2 |
100.000 |
104109,0 |
108392,0 |
99824,0 |
14,00 |
1195,0 |
|
Z nameraných hodnôt môžeme vidieť, že súčet a, b, c porovnaní je približne rovný 3-násobku dĺžky prehľadávaného reťazca. Porovnania d súvisia s vytváraním pomocnej tabuľky. |
|
Počet porovnaní, cyklov a času trvania algoritmu pre veľkosť abecedy=3 znaky, veľkosť vzoru=9 znakov. |
počet znakov v prehľadávanom reťazci |
p_a_porovnani_ |
p_b_porovnani_ |
p_c_porovnani_ |
p_d_porovnani_ |
čas |
10 |
11,00 |
12,00 |
8,000 |
39,00 |
0,4646 |
100 |
108,0 |
144,0 |
70,00 |
39,00 |
2,015 |
1.000 |
1088,0 |
1462,0 |
712,0 |
39,00 |
17,73 |
10.000 |
10967,0 |
14738,0 |
7194,0 |
39,00 |
175,9 |
100.000 |
109707,0 |
147599,0 |
71813,0 |
39,00 |
1769,0 |
|
Z nameraných hodnôt môžeme vidieť, že súčet a, b, c porovnaní je približne rovný 3-násobku dĺžky prehľadávaného reťazca. Porovnania d súvisia s vytváraním pomocnej tabuľky. |
|
Počet porovnaní, cyklov a času trvania algoritmu pre veľkosť abecedy=24 znakov, veľkosť vzoru=9 znakov. |
počet znakov v prehľadávanom reťazci |
p_a_porovnani_ |
p_b_porovnani_ |
p_c_porovnani_ |
p_d_porovnani_ |
čas |
10 |
11,00 |
11,00 |
9,000 |
39,00 |
0,4647 |
100 |
102,0 |
107,0 |
95,00 |
39,00 |
1,506 |
1.000 |
1003,0 |
1043,0 |
961,0 |
39,00 |
11,67 |
10.000 |
10021,0 |
10425,0 |
9615,0 |
39,00 |
113,8 |
100.000 |
100187,0 |
104299,0 |
96073,0 |
39,00 |
1143,6 |
|
Z nameraných hodnôt môžeme vidieť, že súčet a, b, c porovnaní je približne rovný 3-násobku dĺžky prehľadávaného reťazca. Porovnania d súvisia s vytváraním pomocnej tabuľky. |
|
|
Závislost dĺžky času trvania algoritmu od veľkosti vstupného pola |
Aj na efektivitu tohto algoritmu má najväčši veľkosť abecedy. Pre veľkosť abecedy 24 znakov je algoritmus evidenetne rýchlejší ako pre veľkosť abecedy 3 znaky. Algoritmus má podľa tohto grafu lineárnu závislosť dĺžky vykonávania od veľkosti prehľadávaného reťaca. Pre malé polia má však na čas vykonávania algoritmu najväčší dopad predpríprava potrebnej tabuľky. |
|
|
10 |
100 |
1.000 |
10.000 |
100.000 |
veľkosť abecedy=3 znaky, dĺžka vzoru=3 znaky |
0,2932 |
2,270 |
21,22 |
211,7 |
2129,0 |
veľkosť abecedy=24 znakov, dĺžka vzoru=3 znaky |
0,2837 |
1,380 |
11,94 |
118,2 |
1195,0 |
veľkosť abecedy=3 znaky, dĺžka vzoru=9 znakov |
0,4646 |
2,015 |
17,73 |
176,0 |
1769,0 |
veľkosť abecedy=24 znakov, dĺžka vzoru=9 znakov |
0,4647 |
1,506 |
11,67 |
113,8 |
1144,0 |
|
|
|
Poznámka: Algoritmy boli testované na počítači s procesorom AMD Athlon(tm) XP 1700+ a s 256 MB operačnou pamäťou pod operačným systémom Windows XP. Všetky časy uvedené v tabuľke sú v mikrosekundách. |