Data Structure (3) Hash Table (ํ•ด์‹œ ํ…Œ์ด๋ธ”)

    ๋ฐ˜์‘ํ˜•

    ๐Ÿ“ŒHash ๊ตฌ์กฐ

    • Hash Table: key์— data(value)๋ฅผ ์ €์žฅํ•˜๋Š” ๋ฐ์ดํ„ฐ ๊ตฌ์กฐ
    • ex) Python์˜ Dictionary : key์™€ value๋ฅผ ๊ฐ€์ง€๊ณ  ์žˆ๋Š” ๋ฐ์ดํ„ฐ ํƒ€์ž…์œผ๋กœ, key๊ฐ’์„ ํ†ตํ•ด value๋ฅผ ๋ฐ”๋กœ ๊บผ๋‚ผ ์ˆ˜ ์žˆ์Œ (Python์—์„œ๋Š” hash๊ตฌํ˜„ ์—†์ด ๋ฐ”๋กœ dictionary ์‚ฌ์šฉํ•˜๋ฉด ๋จ)
    • ๋ณดํ†ต ๋ฏธ๋ฆฌ hash table์˜ ํฌ๊ธฐ๋งŒํผ ๋ฐฐ์—ด ์ƒ์„ฑ ํ›„ ์‚ฌ์šฉ (๊ณต๊ฐ„๊ณผ ํƒ์ƒ‰ ์‹œ๊ฐ„์„ ๋งž๋ฐ”๊พธ๋Š” ๊ธฐ๋ฒ•)

     

    ๐Ÿ“Œ์šฉ์–ด

    • hash: random ๊ฐ’์„ ๊ณ ์ • ๊ธธ์ด๋กœ ๋ณ€ํ™˜ํ•˜๋Š” ๊ฒƒ (๋‹จ๋ฐฉํ–ฅ ์•”ํ˜ธํ™” ๊ธฐ๋ฒ•์œผ๋กœ, ํ•ด์‹œ ์•Œ๊ณ ๋ฆฌ์ฆ˜์„ ์ด์šฉํ•˜์—ฌ ๊ณ ์ •๋œ ๊ธธ์ด์˜ ์•”ํ˜ธํ™”๋œ ๋ฌธ์ž์—ด๋กœ ๋ณ€ํ™˜)
    • hash table:
    • hashing function: key์— ๋Œ€ํ•ด ์‚ฐ์ˆ  ์—ฐ์‚ฐ์„ ์ด์šฉํ•ด ๋ฐ์ดํ„ฐ ์œ„์น˜๋ฅผ ์ฐพ์„ ์ˆ˜ ์žˆ๋Š” ํ•จ์ˆ˜, ์ฆ‰ ์ž„์ด์ด ๊ธธ์ด์˜ ๋ฐ์ดํ„ฐ๋ฅผ ๊ณ ์ •๋œ ๊ธธ์ด์˜ ๋ฐ์ดํ„ฐ๋กœ ๋งคํ•‘ํ•˜๋Š” ํ•จ์ˆ˜ (key๋ฅผ ์ž…๋ ฅ์œผ๋กœ ๋ฐ›์•„ hash table์˜ ํŠน์ • ์ฃผ์†Œ๊ฐ’(hash value / hash address)๋ฅผ return)
    • key: ๋งคํ•‘ ์ „ ์›๋ž˜ ๋ฐ์ดํ„ฐ ๊ฐ’
    • hash value / hash address: ๋งคํ•‘ ํ›„ ๋ฐ์ดํ„ฐ ๊ฐ’(key๋ฅผ hashing function์œผ๋กœ ์—ฐ์‚ฐํ•˜์—ฌ ๋‚˜์˜จ ๊ฐ’), hash value๋กœ hash table์—์„œ ํ•ด๋‹น key์— ๋Œ€ํ•œ ๋ฐ์ดํ„ฐ ์œ„์น˜๋ฅผ ์ผ๊ด€์„ฑ์žˆ๊ฒŒ ๊ฒ€์ƒ‰ ๊ฐ€๋Šฅ
    • slot: ํ•œ ๊ฐœ์˜ ๋ฐ์ดํ„ฐ๋ฅผ ์ €์žฅํ•  ์ˆ˜ ์žˆ๋Š” ๊ณต๊ฐ„

    ์ž„์˜์˜ ๊ธธ์ด์˜ ๋ฐ์ดํ„ฐ๋ฅผ ๊ณ ์ •๋œ ๊ธธ์ด์˜ ๋ฐ์ดํ„ฐ๋กœ ๋งคํ•‘ํ•˜๋Š” ํ•จ์ˆ˜

    ๋งคํ•‘ ์ „ ์›๋ž˜ ๋ฐ์ดํ„ฐ์˜ ๊ฐ’: key, ๋งคํ•‘ ํ›„ ๋ฐ์ดํ„ฐ์˜ ๊ฐ’์„ hash value, ๋งคํ•‘ํ•˜๋Š” ๊ณผ์ • hashing

    image

    ๐Ÿ“ŒHash Table์˜ ์žฅ๋‹จ์ ๊ณผ ์ฃผ์š” ์šฉ๋„

    • ์žฅ์ 
      • ๊ฒ€์ƒ‰ ์†๋„๊ฐ€ ์—„์ฒญ ๋น ๋ฅด๋‹ค. (๋ฐ์ดํ„ฐ ์ €์žฅ/์ฝ๊ธฐ ์†๋„๊ฐ€ ์—„์ฒญ ๋น ๋ฅด๋‹ค!)
        (array์—์„œ data๋ฅผ ์ฐพ์œผ๋ ค๋ฉด ์•ž์—์„œ๋ถ€ํ„ฐ ์ญˆ์šฐ์šฐ-์šฑ ์ฐพ์•„์•ผ ํ•˜์ง€๋งŒ hash table์—์„œ๋Š” data๋ฅผ ์ฝ์œผ๋ฉด ๊ทธ data์— ๋Œ€์‘ํ•˜๋Š” key๋ฅผ ์ž๋™์œผ๋กœ ์ถ”์ถœํ•˜๊ณ  ๊ทธ key๋ฅผ hash function์— ๋„ฃ์–ด ๋ฐ์ดํ„ฐ ์ €์žฅ ์œ„์น˜๋ฅผ ๋ฐ”๋กœ ๋ฐ˜ํ™˜๋ฐ›์•„ ๊ณง๋ฐ”๋กœ ํƒ์ƒ‰์ด ๊ฐ€๋Šฅํ•˜๋‹ค.)
      • ์ค‘๋ณต ์ฒ˜๋ฆฌ๊ฐ€ ์‰ฝ๋‹ค.
    • ๋‹จ์ 
      • ์ €์žฅ๊ณต๊ฐ„์ด ๋‚ด๊ฐ€ ์ €์žฅํ•˜๊ณ ์ž ํ•˜๋Š” data ์ž์ฒด์˜ size๋ณด๋‹ค ํฐ ๊ฒƒ์ด ์ผ๋ฐ˜์ ์ด๋‹ค.
      • ์—ฌ๋Ÿฌ ํ‚ค์— ํ•ด๋‹นํ•˜๋Š” ์ฃผ์†Œ๊ฐ€ ๋™์ผํ•  ๊ฒฝ์šฐ ์ถฉ๋Œ์„ ํ•ด๊ฒฐํ•˜๊ธฐ ์œ„ํ•œ ๋ณ„๋„ ์ž๋ฃŒ๊ตฌ์กฐ๊ฐ€ ํ•„์š”ํ•˜๋‹ค. (-> ์ถฉ๋Œ ํ•ด๊ฒฐ์„ ์œ„ํ•œ ๊ฐ€์žฅ ๊ฐ„๋‹จํ•œ ๋ฐฉ๋ฒ•์€ ๋‹จ์ˆœํžˆ ์ €์žฅ๊ณต๊ฐ„์„ ๋Š˜๋ฆฌ๋Š” ๊ฒƒ์ด๋‹ค.)
    • ์ฃผ์š” ์šฉ๋„
      • ๊ฒ€์ƒ‰์ด ํ•„์š”ํ•œ ๊ฒฝ์šฐ
      • ์ €์žฅ, ์‚ญ์ œ, ์ฝ๊ธฐ๊ฐ€ ํ•„์š”ํ•œ ๊ฒฝ์šฐ
      • cash ๊ตฌํ˜„์ด ํ•„์š”ํ•œ ๊ฒฝ์šฐ (์‰ฌ์šด ์ค‘๋ณต ์ฒ˜๋ฆฌ)

     

    ๐Ÿ“ŒHash ๊ตฌํ˜„

    
    def get_key(data):
        return hash(data)
    
    def hash_function(key):
        return key % 8 #8๋กœ ๋‚˜๋ˆˆ ๋‚˜๋จธ์ง€๋ฅผ hash value๋กœ
    
    def save_data(data, value):
        hash_address = hash_function(get_key(data)) #key๊ฐ’์„ hash function์— ๋„ฃ์–ด hash value(hash address)๊ฐ’ ๋งŒ๋“ค๊ธฐ
        hash_table[hash_address] = value
    
    def read_data(data):
        hash_address = hash_function(get_key(data))
        return hash_table[hash_address]
    
    • hash table size๋งŒํผ์˜ list๋ฅผ ๋ฏธ๋ฆฌ ์ƒ์„ฑํ•ด์•ผ ํ•จ
    • get_key(): python ๋‚ด์žฅ ํ•จ์ˆ˜ hash()๋ฅผ ์ด์šฉํ•ด data์˜ ๊ณ ์œ  key๊ฐ’์„ ๋ฆฌํ„ด ๋ฐ›๋Š”๋‹ค
    • hash_function(): ๋‚˜๋จธ์ง€ ๊ฐ’์„ ์ด์šฉํ•œ ์ดˆ๊ฐ„๋‹จ hash function
      (hash function ๊ณ ์•ˆ ๊ธฐ๋ฒ•์€ ๋‹ค์–‘ํ•˜์ง€๋งŒ ๊ฐ€์žฅ ๊ฐ„๋‹จํ•œ ๋ฐฉ์‹์€ division๋ฒ•)
    • save_data(): data์™€ value๋ฅผ ์ž…๋ ฅ์œผ๋กœ ๋ฐ›๊ณ , ํ•ด๋‹น data์— ๋Œ€ํ•œ key๋ฅผ hashing function์œผ๋กœ hash ์ฃผ์†Œ๋ฅผ ํŠน์ •ํ•˜๊ณ  ๊ฑฐ๊ธฐ์— value๋ฅผ ์ €์žฅํ•˜๋Š” ํ•จ์ˆ˜
    • read_data(): data๋ฅผ ์ž…๋ ฅ์œผ๋กœ ๋ฐ›๊ณ , ํŠน์ • ์ฃผ์†Œ์— ์ €์žฅ๋œ data์— ํ•ด๋‹นํ•˜๋Š” value๊ฐ’์„ ๋ฆฌํ„ดํ•˜๋Š” ํ•จ์ˆ˜

     

    ๐Ÿ“ŒHash Collision ํ•ด๊ฒฐ ์•Œ๊ณ ๋ฆฌ์ฆ˜

    ํ•œ ๊ฐœ ์ด์ƒ์˜ data๊ฐ€ ์ค‘๋ณต๋˜์–ด ๋™์ผํ•œ address์— ์ €์žฅ๋˜๋Š” ๊ฒฝ์šฐ, hash collision ๋ฐœ์ƒ

    1) Chaining ๊ธฐ๋ฒ•

    • Open Hashing ๊ธฐ๋ฒ• (hash table ์ €์žฅ๊ณต๊ฐ„ ์™ธ์˜ ๊ณต๊ฐ„์„ ํ™œ์šฉํ•˜๋Š” ๊ธฐ๋ฒ•: ์ถฉ๋Œ์ด ๋ฐœ์ƒํ•˜๋ฉด ์ถ”๊ฐ€ ๊ณต๊ฐ„์„ ํ™•๋ณดํ•˜์—ฌ ์ €์žฅ)
    • ์ถฉ๋Œ์ด ์ผ์–ด๋‚˜๋ฉด, linked list๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋ฐ์ดํ„ฐ๋ฅผ ์ถ”๊ฐ€๋กœ ๋’ค์— ์—ฐ๊ฒฐ์‹œ์ผœ์„œ ์ €์žฅํ•˜๋Š” ๋ฐฉ๋ฒ•
      (linked list๋ฅผ ์‚ฌ์šฉํ•˜๊ธฐ ๋•Œ๋ฌธ์— ๋ฏธ๋ฆฌ ์ €์žฅ๊ณต๊ฐ„์„ ์žก์•„๋†“์„ ํ•„์š”์—†์ด, ์ถฉ๋Œ์ด ๋‚  ๋•Œ๋งˆ๋‹ค๋งŒ ์ถ”๊ฐ€ํ•˜๋ฉด ๋จ)

     

    ๊ตฌํ˜„
    
    def get_key(data):
        return hash(data)
    
    def hash_function(key):
        return key % 8
    
    def save_data(data, value):
        index_key = get_key(data) #key๋ฅผ ๋ณ„๋„์˜ ๋ณ€์ˆ˜์— ์ €์žฅ
        hash_address = hash_function(index_key)
        if hash_table[hash_address] != 0: #hash table์— data๊ฐ€ ๋“ค์–ด์žˆ์œผ๋ฉด (์ถฉ๋Œ์ด ๋ฐœ์ƒํ•˜๋ฉด)
            for index in range(len(hash_table[hash_address])): #์ง€๊ธˆ ์ถฉ๋Œ์ด ์ผ์–ด๋‚œ address์— data๊ฐ€ ์–ผ๋งˆ๋‚˜ ์ €์žฅ๋˜์–ด ์žˆ๋Š”์ง€ ํ™•์ธ
                if hash_table[hash_address][index][0] == index_key: #key๊ฐ’์ด ์ค‘๋ณต์ด๋ฉด value๋ฅผ update
                    hash_table[hash_address][index][1] = value
                    return
            hash_table[hash_address].append([index_key, value]) #key๊ฐ’์ด ์ค‘๋ณต์ด ์•„๋‹ˆ๋ฉด append(๋’ค์— ์ถ”๊ฐ€) -> ํ•˜๋‚˜์˜ slot์„ ์ชผ๊ฐœ์„œ key, value๋ฅผ ๊ฐ๊ฐ ์ €์žฅ(list์•ˆ์— list)
        else: #slot์— ๋ฐ์ดํ„ฐ๊ฐ€ ์—†์œผ๋ฉด(์ถฉ๋Œ์ด ์—†์œผ๋ฉด) ๊ทธ๋ƒฅ ๋ฐ”๋กœ ๋„ฃ๊ธฐ
            hash_table[hash_address] = [[index_key, value]] 
    
    def read_data(data):
        index_key = get_key(data)
        hash_address = hash_function(index_key)
    
        if hash_table[hash_address] != 0:
            for index in range(len(hash_table[hash_address])):
                if hash_table[hash_address][index][0] == index_key:
                    return hash_table[hash_address][index][1]
            return None
        else:
            return None
    

     

    save_data()
    • ๊ณ ์œ  key๊ฐ’์„ value๊ฐ€ ๋“ค์–ด์žˆ๋Š” slot์— ๊ฐ™์ด ์ €์žฅํ•ด์•ผ ํ•˜๊ธฐ ๋•Œ๋ฌธ์— index_key๋ณ€์ˆ˜์— ๋”ฐ๋กœ ์ €์žฅํ•ด์•ผ ํ•œ๋‹ค. -> ๊ฐ™์€ adress์— ์ €์žฅ๋˜์–ด ์žˆ์„ ๋•Œ index_key๋กœ ๋‚ด๊ฐ€ ์›ํ•˜๋Š” ๊ฐ’์„ ํƒ์ƒ‰ํ•ด์•ผ ํ•˜๊ฒŒ ๋•Œ๋ฌธ
    • ์ฒซ๋ฒˆ์งธ if๋ฌธ์€ ์ถฉ๋Œ์ด ์ผ์–ด๋‚˜๋Š”์ง€, ์•„๋‹Œ์ง€๋ฅผ ํ™•์ธํ•˜๊ธฐ ์œ„ํ•จ
    • ์ถฉ๋Œ์ด ์ผ์–ด๋‚˜๋ฉด, for๋ฌธ์„ ํ†ตํ•ด ์ถฉ๋Œ์ด ์ผ์–ด๋‚œ address์— ํ˜„์žฌ ๋ฐ์ดํ„ฐ๊ฐ€ ์–ผ๋งˆ๋‚˜ ์ €์žฅ๋˜์–ด ์žˆ๋Š”์ง€ ํ™•์ธ
    • address๊ฐ€ ๊ฐ™์œผ๋ฏ€๋กœ ํƒ์ƒ‰์„ ์œ„ํ•ด์„œ ํ•˜๋‚˜์˜ slot์— key์™€ value๊ฐ’์„ ๊ฐ™์ด ์ €์žฅํ•ด ์ฃผ์–ด์•ผ ํ•จ (list์•ˆ์— list)

     

    read_data()
    • for๋ฌธ์œผ๋กœ ๋‚ด๊ฐ€ ์ฝ์–ด์˜ค๊ณ  ์‹ถ์€ ๋ฐ์ดํ„ฐ๋ฅผ ์ฐพ๊ธฐ๊นŒ์ง€ ๋ฐ˜๋ณต๋ฌธ ์ˆ˜ํ–‰

     

    2) Linear Probing ๊ธฐ๋ฒ•

    • Close Hashing ๊ธฐ๋ฒ• (hash table ์ €์žฅ๊ณต๊ฐ„ ๋‚ด์˜ ๊ณต๊ฐ„์„ ํ™œ์šฉํ•˜๋Š” ๊ธฐ๋ฒ•: ์ถฉ๋Œ์ด ๋ฐœ์ƒํ•˜๋ฉด hash table์•ˆ์˜ ๋ฐ˜ ๊ณต๊ฐ„์„ ์ฐพ์•„์„œ ๊ฑฐ๊ธฐ์— ์ €์žฅํ•˜๋Š” ๋ฐฉ๋ฒ•)
    • ์ถฉ๋Œ์ด ์ผ์–ด๋‚˜๋ฉด, ํ•ด๋‹น hash address์˜ ๋‹ค์Œ address๋ถ€ํ„ฐ ๋งจ ์ฒ˜์Œ ๋‚˜์˜ค๋Š” ๋นˆ ๊ณต๊ฐ„์— ์ €์žฅ(์ €์žฅ๊ณต๊ฐ„ ํ™œ์šฉ๋„๋ฅผ ๋†’์ด๊ธฐ ์œ„ํ•œ ๊ธฐ๋ฒ•)

     

    ๊ตฌํ˜„
    hash_table = list([0 for i in range(8)])
    
    def get_key(data):
        return hash(data)
    
    def hash_function(key):
        return key % 8
    
    def save_data(data, value):
        index_key = get_key(data)
        hash_address = hash_function(index_key)
        if hash_table[hash_address] != 0:
            for index in range(hash_address, len(hash_table)): #ํ˜„์žฌ address๋ถ€ํ„ฐ hash table์„ ๋๊นŒ์ง€ ๋ฐ˜๋ณตํ•˜๋ฉด์„œ
                if hash_table[index] == 0: #๋นˆ๊ณต๊ฐ„ ์ฐพ์œผ๋ฉด
                    hash_table[index] = [index_key, value] #๊ฑฐ๊ธฐ์— ๋ฐ์ดํ„ฐ ๋„ฃ๊ธฐ
                    return
                elif hash_table[index][0] == index_key: #key์ž์ฒด๊ฐ€ ๊ฐ™์œผ๋ฉด value update
                    hash_table[index][1] = value 
                    return
        else: #ํ•ด๋‹น address์— data๊ฐ€ ์•„์˜ˆ ์—†์Œ -> ๋ฐ”๋กœ ๋„ฃ์œผ๋ฉด ๋จ (์ถฉ๋Œ ๋ฐœ์ƒ X)
            hash_table[hash_address] = [index_key, value]
    
    def read_data(data):
        index_key = get_key(data)
        hash_address = hash_function(index_key)
    
    
        if hash_table[hash_address] != 0:
            for index in range(hash_address, len(hash_table)):
                if hash_table[index] == 0: #adress์— ๊ฐ’์ด ์žˆ๊ธด ์žˆ๋Š”๋ฐ ๋‚ด๊ฐ€ ์ฐพ๋Š” ๊ฐ’์€ ์—†์Œ
                    return None
                elif hash_table[index][0] == index_key:
                    return hash_table[index][1]
        else: #์ฝ์–ด์˜ฌ data ์ž์ฒด๊ฐ€ ์•„์˜ˆ ์—†์Œ
            return None
    

     

    save_data()
    • ์ถฉ๋Œํ•œ data๋ฅผ ๋‹ค๋ฅธ ๊ณต๊ฐ„์— ๋„ฃ์–ด์•ผ ํ•˜๋ฏ€๋กœ chaining ๊ธฐ๋ฒ•๊ณผ ๋งˆ์ฐฌ๊ฐ€์ง€๋กœ data์˜ ๊ณ ์œ ํ•œ key๋„ ํ•จ๊ป˜ ์ €์žฅํ•ด์ฃผ์–ด์•ผ ํ•จ (address๊ฐ€ ๊ฐ™์œผ๋ฏ€๋กœ ํƒ์ƒ‰์„ ์œ„ํ•ด์„œ ํ•˜๋‚˜์˜ slot์— key์™€ value๊ฐ’์„ ๊ฐ™์ด ์ €์žฅํ•ด ์ฃผ์–ด์•ผ ํ•จ (list์•ˆ์— list))
    • ์ฒซ๋ฒˆ์งธ if๋ฌธ์€ ์ถฉ๋Œ์ด ์ผ์–ด๋‚˜๋Š”์ง€, ์•„๋‹Œ์ง€๋ฅผ ํ™•์ธํ•˜๊ธฐ ์œ„ํ•จ
    • ์ถฉ๋Œ์ด ์ผ์–ด๋‚˜๋ฉด, for๋ฌธ์„ ํ†ตํ•ด ํ˜„์žฌ address๋ถ€ํ„ฐ hash table ๋๊นŒ์ง€ ๋Œ๋ฉด์„œ ๋นˆ๊ณต๊ฐ„์„ ์ฐพ์œผ๋ฉด ๊ฑฐ๊ธฐ์— ๋ฐ์ดํ„ฐ ๋„ฃ๊ธฐ
    • ๋งŒ์•ฝ key์ž์ฒด๊ฐ€ ๋™์ผํ•˜๋ฉด data value๋ฅผ update

     

    read_data()
    • ์ฒซ๋ฒˆ์งธ if๋ฌธ์€ data๊ฐ€ hash table์— ์žˆ๋Š”์ง€๋ฅผ ๊ฒ€์ƒ‰
    • for๋ฌธ์œผ๋กœ hash table์„ ๋Œ๋ฉด์„œ ๋‚ด๊ฐ€ ์ฐพ๊ณ ์‹ถ์€ ๋ฐ์ดํ„ฐ ์ฐพ๊ธฐ
    • if hash_table[index] == 0: ๊ฐ’์ด 0์ด๋ผ๋Š” ๊ฑด ๋นˆ๊ณต๊ฐ„์ด๋ผ๋Š” ๋œป -> ๋นˆ๊ณต๊ฐ„์ด ๋‚˜์™”๋‹ค๋ฉด ์ด์ „์— ์ด๋ฏธ ์ฐพ์•˜์œผ์•ผ ๋๋Š”๋ฐ, ๋นˆ๊ณต๊ฐ„์ด ๋‚˜์˜ฌ๋•Œ๊นŒ์ง€ ์•„์ง๋„ ๋ชป์ฐพ์•˜๋‹ค๋ฉฐ ๋‚ด๊ฐ€ ์ฐพ๋Š” ๊ฐ’์ด ์—†๋‹ค๋Š” ์–˜๊ธฐ

     

    ๋นˆ๋ฒˆํ•œ ์ถฉ๋Œ์„ ๊ฐœ์„ ํ•˜๋Š” ๋ฐฉ๋ฒ•

    • hashing function ์žฌ์ •์˜
    • hash table ์ €์žฅ๊ณต๊ฐ„ ํ™•๋Œ€def hash_function(key):{% endhighlight %}
    • => ์ €์žฅ๊ณต๊ฐ„↑ → ์ถฉ๋Œ↓, ํƒ์ƒ‰์‹œ๊ฐ„↓ (:hash table์€ ๊ณต๊ฐ„๊ณผ ํƒ์ƒ‰์‹œ๊ฐ„์„ ๋งž๋ฐ”๊พผ๋‹ค)
    • return key % 16
    • {% highlight python %}
      hash_table = list([None for i in range(16)])

     

    ๐Ÿ“Œhashing function๊ณผ ํ‚ค ์ƒ์„ฑ ํ•จ์ˆ˜

    • python์˜ hash()ํ•จ์ˆ˜๋Š” ์‹คํ–‰ํ•  ๋•Œ๋งˆ๋‹ค, ๊ฐ’์ด ๋‹ฌ๋ผ์งˆ ์ˆ˜ ์žˆ์Œ
    • ๋”ฐ๋ผ์„œ SHA(Secure Hash Algorithm) ์‚ฌ์šฉ: ์–ด๋–ค ๋ฐ์ดํ„ฐ๋„ ์œ ์ผํ•œ ๊ณ ์ •๋œ ํฌ๊ธฐ์˜ ๊ณ ์ •๊ฐ’์„ return
    import hashlib
    
    hash_table = list([0 for i in range(8)])
    
    def get_key(data):
            hash_object = hashlib.sha256()
            hash_object.update(data.encode())
            hex_dig = hash_object.hexdigest()
            return int(hex_dig, 16)

     

    ๐Ÿ“Œ์‹œ๊ฐ„๋ณต์žก๋„

    • ์ผ๋ฐ˜์ ์ธ ๊ฒฝ์šฐ(collision์ด ์—†๋Š” ๊ฒฝ์šฐ): $O(1)$ (-> ๋ฐ”๋กœ ํŠน์ •์œ„์น˜์— ์ €์žฅํ•˜๊ณ  ๊ฒ€์ƒ‰ํ•˜๊ธฐ ๋•Œ๋ฌธ์—)
    • ์ตœ์•…์˜ ๊ฒฝ์šฐ(๋ชจ๋‘ collision์ด ๋ฐœ์ƒํ•˜๋Š” ๊ฒฝ์šฐ): $O(n)$

    -> hash table์˜ ๊ฒฝ์šฐ, ์ผ๋ฐ˜์ ์ธ ๊ฒฝ์šฐ๋ฅผ ๊ธฐ๋Œ€ํ•˜๊ณ  ๋งŒ๋“ค๊ธฐ ๋•Œ๋ฌธ์— ์‹œ๊ฐ„ ๋ณต์žก๋„๋Š” $O(1)$์ด๋ผ๊ณ  ํ•  ์ˆ˜ ์žˆ์Œ

     

    ๊ฒ€์ƒ‰์—์„œ array์™€ ๋น„๊ตํ•˜๋ฉด
    • 16๊ฐœ์˜ ๋ฐฐ์—ด์— ๋ฐ์ดํ„ฐ๋ฅผ ์ €์žฅํ•˜๊ณ , ๊ฒ€์ƒ‰: $O(n)$ (-> ๋ชจ๋‘ ํ•œ๋ฒˆ์”ฉ ์ˆœํšŒํ•ด์•ผ ํ•˜๊ธฐ ๋•Œ๋ฌธ์—)
    • 16๊ฐœ์˜ ๋ฐ์ดํ„ฐ ์ €์žฅ๊ณต๊ฐ„์„ ๊ฐ€์ง„ ํ•ด์‰ฌ ํ…Œ์ด๋ธ”์— ๋ฐ์ดํ„ฐ๋ฅผ ์ €์žฅํ•˜๊ณ , ๊ฒ€์ƒ‰: $O(1)$
    ๋ฐ˜์‘ํ˜•

    ๋Œ“๊ธ€