# 2017q1 Homework1 (phonebook) contributed by <`heathcliffYang`> ### Reviewed by `hunng` - 利用多個 hash function 來探討其差異 - 但能簡單介紹一下每個的內容,並在最後圖表中附上所有內容,能更好的看出優劣 - 利用改變不同查詢的值,讓實驗能更符合實際情況 - 因應輸出的值須修改一下 y 軸單位 ## 開發環境 ``` Architecture: x86_64 CPU op-mode(s): 32-bit, 64-bit Byte Order: Little Endian CPU(s): 4 On-line CPU(s) list: 0-3 Thread(s) per core: 2 Core(s) per socket: 2 Socket(s): 1 NUMA node(s): 1 Vendor ID: GenuineIntel CPU family: 6 Model: 58 Model name: Intel(R) Core(TM) i5-3210M CPU @ 2.50GHz Stepping: 9 CPU MHz: 1200.000 CPU max MHz: 3100.0000 CPU min MHz: 1200.0000 BogoMIPS: 4988.88 Virtualization: VT-x L1d cache: 32K L1i cache: 32K![](https://i.imgur.com/qUGUX4K.png) L2 cache: 256K L3 cache: 3072K NUMA node0 CPU(s): 0-3 ``` ### cache ``` Handle 0x0001, DMI type 7, 19 bytes Cache Information Socket Designation: Unknown Configuration: Enabled, Not Socketed, Level 1 Operational Mode: Write Back Location: Internal Installed Size: 32 kB Maximum Size: 32 kB Supported SRAM Types: Asynchronous Installed SRAM Type: Asynchronous Speed: Unknown Error Correction Type: Single-bit ECC System Type: Other Associativity: 16-way Set-associative ``` ## 原版 Performance counter stats for './phonebook_orig' (100 runs): 2,037,678 cache-misses # 95.827 % of all cache refs ( +- 0.65% ) 2,126,412 cache-references ( +- 0.65% ) 260,791,029 instructions # 1.44 insns per cycle ( +- 0.02% ) 180,682,430 cycles ( +- 0.27% ) 0.069068516 seconds time elapsed ( +- 1.85% ) ## 其他資料結構與搜尋方法 ## hash function 版本的優化 1. 將資料檢索與詳細資料分開,以 `entry` 的大小簡化為基本,繼續之前沒能實作的 hash function 的方法。 2. `TABLE_SIZE` 的值會影響到 `append()` 所花的時間與 cache miss 3. 不同的 hash function 4. Hash function 的 distribution 的實驗,計算最小可容忍的 table size - 修正 hash function 優化版本中 append() 的失誤:沒有將 list 正確 link 起來;之所以此次找的字串 "zyxel" 無法檢測出 append() 不正確是因為這個字串是很後面才被 append 的,所以他的資料不會被覆蓋掉,也就找的到。 因此,當寫完優化版本之後,為確認其正確性,還是取 dataset 中相距較遠的樣本來檢測比較好。 ![](https://i.imgur.com/NbAFUA3.png) - 關於 append() ,一開始的直覺是:從尾端新增,但這樣 append() 所花的時間高達 0.2 sec ,不過其實沒這個必要,因為可以從前端 insert ,雖然時間還是因為多一些判斷而偏高,但仍因為 zyxel 在後面的原因,所以 findName() 幾乎為最佳。 ``` Performance counter stats for './phonebook_opt' (100 runs): 412,103 cache-misses # 42.583 % of all cache refs ( +- 0.76% ) 967,771 cache-references ( +- 0.26% ) 233,042,376 instructions # 1.41 insns per cycle ( +- 0.02% ) 165,053,962 cycles ( +- 0.34% ) 0.058836808 seconds time elapsed ( +- 1.34% ) ``` - cache miss 下降顯著,但仍有改進空間。 ### Hash table size 的影響探討 - based on BKDR hash function - append() 所花時間 ![](https://i.imgur.com/GBqtO1l.png) - cache-misses (%) ![](https://i.imgur.com/CCt56FX.png) ### 不同 hash function 與 distibution 的觀察 >什麼是 the number of layers (Y軸) >[color=red][name=課程助教] >我喜歡他的圖[name=亮谷] >To 課程助教:因為想知道 word 被分配到各個 key 的情形[name=楊惟晶] * TABLE_SIZE 皆為 30000 1. BKDR cache-misses 52.208% ![](https://i.imgur.com/IOPU8kY.png) ![](https://i.imgur.com/mX2l4Wm.png) 2. SDBM cache-misses 59.723% ![](https://i.imgur.com/u9E4jrU.png) ![](https://i.imgur.com/xBSkQMW.png) 3. RS cache-misses 57.723% ![](https://i.imgur.com/GITU7fW.png) ![](https://i.imgur.com/1Vy5P3o.png) 4. JS 49.795% ![](https://i.imgur.com/LjQXtD7.png) ![](https://i.imgur.com/K1IbJBt.png) 5. PJW 53.365% ![](https://i.imgur.com/BWfO3Qe.png) ![](https://i.imgur.com/uMQLbae.png) 6. ELF 50.140% ![](https://i.imgur.com/eKXf4Uo.png) ![](https://i.imgur.com/bcR9OEy.png) 7. ==DJB== 50.343% ![](https://i.imgur.com/mKxWytN.png) ![](https://i.imgur.com/mT39bUI.png) 8. AP 51.845% ![](https://i.imgur.com/eeeccWa.png) ![](https://i.imgur.com/lWNiunX.png) ## Dataset 的討論 - /dictionary/words.txt -> 349900 個 words - opt : hash function BKDR version, TABLE_SIZE 為 20000 1. 為於資料 50% 位置的 "lonely" ![](https://i.imgur.com/6PR8MLW.png) - **cache-misses** 的方面: orig : 94.337%, opt : 36.001% orig 的搜尋時間易受 target 位置改變影響;對 opt 來說,只要分佈得夠平均,尋找資料的時間都很短,變化不大。 - /dictionary/all-names.txt -> 16750 個 names - opt : hash function BKDR version,TABLE_SIZE 為 20000 - Distribution of all-names.txt ![](https://i.imgur.com/3eJ77Kt.png) 50% : erika, 25% : ford, 75% : catherine 1. ford ![](https://i.imgur.com/1TLVxhg.png) - **cache-misses** 的方面: orig : 69.954%, opt : 43.364% 2. erika ![](https://i.imgur.com/f03RAlL.png) - **cache-misses** 的方面: orig : 73.360%, opt : 43.553% 3. catherine ![](https://i.imgur.com/btUBNaq.png) - **cache-misses** 的方面: orig : 72.149%, opt : 48.895% 因為 dataset 太小,append() 都沒有花很多時間;而就 findName()來說,只要 target 越前面,對 orig 版本越有利,而 opt 則是穩定的少。 ## 關於 cache-misses 此次嘗試只改變 opt 的搜尋方法,而不改變資料的結構 opt : BKDR + TABLE_SIZE 為 20000 1. append() + findName() ![](https://i.imgur.com/bOfgr8i.png) Performance counter stats for './phonebook_opt' (100 runs): 1,163,149 cache-misses # 64.363 % of all cache refs ( +- 0.16% ) 1,807,180 cache-references ( +- 0.12% ) 255,560,409 instructions # 1.18 insns per cycle ( +- 0.12% ) 216,628,926 cycles ( +- 0.53% ) 0.103203648 seconds time elapsed ( +- 1.99% ) 2. 只有append() Performance counter stats for './phonebook_opt' (100 runs): 1,159,457 cache-misses # 63.565 % of all cache refs ( +- 0.19% ) 1,824,048 cache-references ( +- 0.12% ) 254,958,193 instructions # 1.19 insns per cycle ( +- 0.08% ) 215,133,335 cycles ( +- 0.42% ) 0.101813265 seconds time elapsed ( +- 2.16% ) Performance counter stats for './phonebook_orig' (100 runs): 908,096 cache-misses # 93.467 % of all cache refs ( +- 0.05% ) 971,572 cache-references ( +- 0.10% ) 201,187,670 instructions # 1.50 insns per cycle ( +- 0.03% ) 133,950,753 cycles ( +- 0.20% ) 0.052471375 seconds time elapsed ( +- 2.70% ) - 去除掉其他動作(檔案寫入等等),讓 1 & 2 的情況差異只多了一個 findName()。 ### append() 與 findName() 的 cache-misses 觀察 - opt: cache-misses 只少了 3692 次 (只佔約0.32%)影響很小 ### append() 各種因素的比較 - 在同樣的資料結構下: 兩種不同的 appenf() 方法,從 orig -> opt 增加了 27.68% 的 cache-misses,可見 hash function 的資料儲存有一定的效能犧牲 - opt 的不同 TABLE_SIZE 的影響 (資料結構未改變) 10000 : 987,147 20000 : 1,159,475 30000 : 1,270,889 在 array 之間的移動有相當的影響。 - OPT 版本的資料結構改變的影響(TABLE_SIZE = 20000): 1,159,475 -> 35,541 --- - 資料一次從記憶體下層轉移到記體上層的單位定作 block。 >> 跟一開始的檔案系統設定的 block size = 4096 bytes 有不一樣嗎? >> [name=楊惟晶] ## Fuzzy Search - Soundex 這學期希望自己著重在實際把演算法變成程式碼,而不是找到可以用的複製貼上,寫程式能力太弱了需要練習。 從構思到 debug 完居然花了一整天。 - /dictionary/all-names.txt , 找的字 = zuzana (最後一個) ![](https://i.imgur.com/VfMD40K.png) ![](https://i.imgur.com/4kpoPyj.png) - append() 的時間多了整整 46%,而從 distribution 的狀況來看,可以隱約看出端倪,分佈的跨度非常大,極度不平均,這是因為英文上有些"聽起來很像"的名字,所以依照 soundex 會得到一樣的編碼。 - Example: find : abby Similar answer: abby, 100 abbie, 100 abbi, 100 abbey, 100 abbe, 100 - TABLE_SIZE 的變化。 - 20000 Performance counter stats for './phonebook_opt' (100 runs): 41,700 cache-misses # 57.339 % of all cache refs ( +- 0.65% ) 72,724 cache-references ( +- 2.26% ) 38,520,996 instructions # 1.68 insns per cycle ( +- 0.01% ) 22,983,744 cycles ( +- 1.21% ) 0.008330655 seconds time elapsed ( +- 1.23% ) - 3000 Performance counter stats for './phonebook_opt' (100 runs): 25,337 cache-misses # 54.181 % of all cache refs ( +- 0.83% ) 46,763 cache-references ( +- 2.82% ) 21,227,533 instructions # 1.41 insns per cycle ( +- 0.01% ) 15,037,622 cycles ( +- 1.18% ) 0.005637389 seconds time elapsed ( +- 1.41% ) ![](https://i.imgur.com/qawN8eV.png) table size 愈小,出現愈高的峰值,某些"聽起來"可能的字愈多的名字,就可能會找到不省人事。 [main.c & Makefile參考來源](https://github.com/0140454/phonebook-1/blob/master/main.c) [smaz 字串壓縮參考來源](https://github.com/antirez/smaz)