[์ž๋ฃŒ๊ตฌ์กฐ] 05. Hash Table

2021. 8. 27. 08:00ใ†์ฝ”๋”ฉ ํ…Œ์ŠคํŠธ ์ค€๋น„/์ž๋ฃŒ๊ตฌ์กฐ

728x90
๋ฐ˜์‘ํ˜•

์•ˆ๋…•ํ•˜์„ธ์š”? ์ฃผ๋‹ˆํ•˜๋ž‘ ์ž…๋‹ˆ๋‹ค.

์˜ค๋Š˜์€ ์ž๋ฃŒ๊ตฌ์กฐ์—์„œ Hash Table์— ๋Œ€ํ•ด์„œ ๊ณต๋ถ€ ํ•ด ๋ณด๋„๋ก ํ•  ๊ฒƒ์ด์—์š”!

์ œ๊ฐ€ ์ž‘์„ฑํ•œ ์ฝ”๋“œ๊ฐ€ ๊ถ๊ธˆํ•˜์‹œ๋‹ค๋ฉด? ์ฃผ๋‹ˆํ•˜๋ž‘์˜ ๊นƒ ํ—ˆ๋ธŒ์— ๊ด€์‹ฌ์„ ์ฃผ์„ธ์š”!

ํ•ด์‹œ ํ•จ์ˆ˜์— ๋Œ€ํ•œ ๊ฐœ๋…์„ ์ž˜ ๋ชจ๋ฅด์‹ ๋‹ค๋ฉด [์ •๋ณด๋ณด์•ˆ] ํ•ด์‹œํ•จ์ˆ˜ ๊ฐœ๋…์— ๊ด€์‹ฌ์„ ์ฃผ์„ธ์š”!

๋ฐ”๋กœ ์‹œ์ž‘ ํ•ด ๋ณด๊ฒ ์Šต๋‹ˆ๋‹ค!



 

 


 

 

 

๐Ÿ“Œ Hash Table


 

    ๐Ÿ“ Hash ๊ตฌ์กฐ

Hash Table์€ Key์™€ Data๋ฅผ ์ €์žฅํ•˜๋Š” Data ๊ตฌ์กฐ์ธ ๊ฒƒ์ด์—์š”.

JAVA๋กœ ๋ณด๋ฉด Hash Map์ด ๋  ๊ฒƒ์ด๊ณ , Python์—์„œ๋Š” Dictionary ๊ตฌ์กฐ๊ฐ€ ๋  ๊ฒƒ์ด์—์š”!

  • Key๋ฅผ ํ†ตํ•ด ๋ฐ”๋กœ Data๋ฅผ ๋ฐ›์•„์˜ฌ ์ˆ˜ ์žˆ์œผ๋ฏ€๋กœ, ์†๋„๊ฐ€ ํš๊ธฐ์ ์œผ๋กœ ๋น ๋ฅด๋‹ค
  • Python Dictionary(์‚ฌ์ „) Type Hash Table Exam : Key๋ฅผ ๊ฐ€์ง€๊ณ  ๋ฐ”๋กœ Value๋ฅผ ๊บผ๋‚ธ๋‹ค.
  • ๋ณดํ†ต ๋ฐฐ์—ด๋กœ ๋ฏธ๋ฆฌ Hash Table ํฌ๊ธฐ ๋งŒํผ ์ƒ์„ฑ ๋’ค์— ์‚ฌ์šฉ (๊ณต๊ฐ„๊ณผ ํƒ์ƒ‰ ์‹œ๊ฐ„์„ ๋งž๋ฐ”๊พธ๋Š” ๊ธฐ๋ฒ•)
  • ๋‹จ, Python์ด๋‚˜, JAVA ๋“ฑ Hash๋ฅผ ๋ณ„๋„ ๊ตฌํ˜„ํ•  ์ด์œ ๊ฐ€ ์—†๋‹ค. (Dictionary, Hash Map ์‚ฌ์šฉ)

 

    ๐Ÿ“ ์ฃผ์š” ์šฉ์–ด

  • Hash : ์ž„์˜ ๊ฐ’์„ ๊ณ ์ • ๊ธธ์ด๋กœ ๋ณ€ํ™˜ (์ž…๋ ฅ ๊ฐ’์ด ์•„๋ฌด๋ฆฌ ํฌ๋”๋ผ๋„ ๊ณ ์ •๋œ ๊ฐ’์œผ๋กœ Out์„ ํ•œ๋‹ค. SHA -256์˜ ๊ฒฝ์šฐ Out ํฌ๊ธฐ๊ฐ€ 256)
    ์ž…๋ ฅ ๊ฐ’์„ Block์ด๋ผ ๋ถ€๋ฅธ๋‹ค.
  • Hash Table : Key Value์˜ ์—ฐ์‚ฐ์— ์˜ํ•ด ์ง์ ‘ ์ ‘๊ทผ์ด ๊ฐ€๋Šฅํ•œ Data ๊ตฌ์กฐ
  • Hashing Function(ํ•ด์‹ฑ ํ•จ์ˆ˜) : Key๋ฅผ Hashing Function์œผ๋กœ ์—ฐ์‚ฐํ•˜์—ฌ Hash Value๋ฅผ ์•Œ์•„๋‚ด๊ณ , ์ด๋ฅผ ๊ธฐ๋ฐ˜์œผ๋กœ Hash Table์—์„œ ํ•ด๋‹น Key์— ๋Œ€ํ•œ Data ์œ„์น˜๋ฅผ ์ผ๊ด€์„ฑ ์žˆ๊ฒŒ ์ฐพ์„ ์ˆ˜ ์žˆ๋‹ค.
  • Slot : ํ•œ ๊ฐœ์˜ Data๋ฅผ ์ €์žฅํ•  ์ˆ˜ ์žˆ๋Š” ๊ณต๊ฐ„
  • ์ €์žฅํ•  Data์— ๋Œ€ํ•ด Key๋ฅผ ์ถ”์ถœํ•  ์ˆ˜ ์žˆ๋Š” ๋ณ„๋„ Function(ํ•จ์ˆ˜)๋„ ์กด์žฌํ•  ์ˆ˜ ์žˆ๋‹ค.

 

 

 

 

 

 

    ๐Ÿ“ ์ž๋ฃŒ ๊ตฌ์กฐ Hash Table ์žฅ, ๋‹จ์  ๋ฐ ์ฃผ์š” ์šฉ๋„

          ๐Ÿ‘‰ ์žฅ์ 

  • Data ์ €์žฅ / ์ฝ๊ธฐ ์†๋„๊ฐ€ ๋น ๋ฅด๋‹ค. ( ๊ฒ€์ƒ‰ ์†๋„๊ฐ€ ํ—ˆ๋ฒŒ๋‚˜๊ฒŒ ๋น ๋ฅด๋‹ค.)
  • Hash๋Š” Key์— ๋Œ€ํ•œ Data๊ฐ€ ์žˆ๋Š”์ง€ (์ค‘๋ณต) ํ™•์ธ์ด ์‰ฝ๋‹ค.

       

          ๐Ÿ‘‰ ๋‹จ์ 

  • ์ผ๋ฐ˜์ ์œผ๋กœ ์ €์žฅ๊ณต๊ฐ„์ด ์ข€ ๋” ๋งŽ์ด ํ•„์š”
  • ์—ฌ๋Ÿฌ Key์— ํ•ด๋‹นํ•˜๋Š” ์ฃผ์†Œ๊ฐ€ ๋™์ผํ•  ๊ฒฝ์šฐ ์ถฉ๋Œ์„ ํ•ด๊ฒฐํ•˜๊ธฐ ์œ„ํ•œ ๋ณ„๋„ ์ž๋ฃŒ๊ตฌ์กฐ ํ•„์š”

 

          ๐Ÿ‘‰ ์ฃผ์š” ์šฉ๋„

  • ๊ฒ€์ƒ‰์ด ๋งŽ์ด ํ•„์š”ํ•œ ๊ฒฝ์šฐ ์‚ฌ์šฉ
  • ์ €์žฅ, ์‚ญ์ œ, ์ฝ๊ธฐ๊ฐ€ ๋นˆ๋ฒˆํ•œ ๊ฒฝ์šฐ ์‚ฌ์šฉ
  • Cache ๊ตฌํ˜„ ์‹œ ์‚ฌ์šฉ (์ค‘๋ณต ํ™•์ธ์ด ์‰ฝ๊ธฐ์— ์‚ฌ์šฉ)

 

 

 

 

 

๋จผ์ € Hash๋ฅผ ์ด์šฉํ•ด์„œ Data๋ฅผ ์ฐพ์„ ๋•Œ, data์— ํ•ด๋‹น('Andy', 'Dave', 'Trump')ํ•˜๋Š” ๊ฒƒ์„ ๋จผ์ € ์ฐพ์œผ๋ฉด ๊ทธ์™€ Matching ๋˜๋Š” Key๋ฅผ ์ฐพ๊ฒŒ ๋˜๊ณ , ๊ทธ Key๋ฅผ ๋จผ์ € ord()๋ฅผ ์ด์šฉํ•˜์—ฌ ๋ฌธ์ž์—ด์„ ASCII Code (์ •์ˆ˜)๋ฅผ ๊ตฌํ•œ ๋‹ค์Œ Hash ํ•จ์ˆ˜์— ๋„ฃ์œผ๋ฉด Division ๋ฐฉ์‹์œผ๋กœ ๋‚˜๋ˆ„๊ธฐ 5๋ฅผ ํ•˜๊ณ , ๋‚˜๋จธ์ง€ ๊ฐ’์„ ์ฐพ๋Š” ๊ฒƒ์ด์—์š”. ๊ทธ๋Ÿฌ๊ณ  ๋‚œ ๋’ค ๊ทธ๊ฒƒ์„ Hash Address๋กœ ์‚ฌ์šฉํ•˜์—ฌ Hash Table์— ์žˆ๋Š” ๋ฒˆํ˜ธ์™€ Matching ์‹œ์ผœ ๊ฐ’์„ ์ฐพ์„ ์ˆ˜ ์žˆ๋‹ต๋‹ˆ๋‹ค!

 

 

์œ„์™€ ๊ฐ™์ด Hash Table์ด ์•„๋‹Œ ๋ฐฐ์—ด์„ ์‚ฌ์šฉํ–ˆ๋‹ค๋ฉด Key(ASCII)์™€ Value๊ฐ€ ๋“ค์–ด๊ฐˆ ๋‘ ๊ฐœ์˜ ๋ฐฐ์—ด์ด ํ•„์š”ํ•˜๊ฒŒ ๋  ๊ฒƒ์ด๊ณ , ๋งŒ์•ฝ Trump๋ฅผ ์ฐพ์œผ๋ ค๋ฉด 16๋ฒˆ์— ๊ฒ€์ƒ‰์ด ์ด๋ค„์–ด ์ ธ์•ผ ํ•˜๋Š” ๋‹จ์ ์ด ์žˆ๋Š” ๊ฒƒ์ด์—์š”.

 

ํ•˜์ง€๋งŒ, Hash๋ฅผ ์ด์šฉํ•˜๋ฉด ํ•ด๋‹น data๋ฅผ ํ†ตํ•ด Matching๋˜๋Š” ๊ฐ’์„ ๋‚ด๋ถ€ ์—ฐ์‚ฐ์œผ๋กœ ๋ฐ”๋กœ ์ฐพ์„ ์ˆ˜ ์žˆ๋Š” ์žฅ์ ์ด ์žˆ๋‹ต๋‹ˆ๋‹ค!

 

์šฐ๋ฆฌ๋Š” ์œ„์— Hash Function์—์„œ Division ๋ฐฉ์‹์„ ์œ„ํ•ด 5๋ฅผ ๋‚˜๋ˆˆ ๊ฒƒ์„ ์•Œ๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค.

๊ทธ๋ฆฌ๊ณ , Hash Table์€ ์ด 5๊ฐœ์˜ ๊ธธ์ด๋ฅผ ๊ฐ€์ง€๊ณ  ์žˆ์ง€์š”.

๋‚ด๊ฐ€ ์ž…๋ ฅํ•  Data๋ณด๋‹ค ์ผ๋ฐ˜์ ์œผ๋กœ ์กฐ๊ธˆ ํฌ๊ฒŒ Hash Table์„ ๋งŒ๋“ค์–ด์•ผ ํ•˜๋Š”๋ฐ, ์—ฌ๊ธฐ์„œ Hash Table์˜ ๋‹จ์ ์„ ์•Œ ์ˆ˜๊ฐ€ ์žˆ๋Š” ๊ฒƒ์ด์—์š”.

์œ„์˜ ๊ทธ๋ฆผ์—์„œ Hash Tabledp 1, 2๋ฒˆ Data๊ฐ€ ๋น„์–ด์žˆ์Œ์—๋„ ๋งŒ๋“ค์–ด ์ค€ ๊ฒƒ์€ ๋งŒ์•ฝ ๋‚ด๊ฐ€ ๋„ฃ์„ Data ๊ฐœ์ˆ˜ ๋งŒํผ ๊ธธ์ด๋ฅผ ์žก๊ฑฐ๋‚˜ ๊ทธ ๋ณด๋‹ค ์ ๊ฒŒ ์žก๊ฒŒ ๋˜๋ฉด '์ถฉ๋Œ'์„ ํ•ด๊ฒฐํ•˜๊ธฐ ์œ„ํ•ด ๋ณ„๋„ ์ž๋ฃŒ ๊ตฌ์กฐ๊ฐ€ ํ•„์š”ํ•ด ์ง€๋Š” ๊ฒƒ์ด์—์š”. ๋งŒ์•ฝ Andy๋ผ๋Š” ๊ฐ’์˜ Key์™€ ์ถ”๊ฐ€๋กœ ๋„ฃ์€ Harang์ด๋ผ๋Š” Data์˜ Key๊ฐ€ ๋™์ผํ•˜๋‹ค๋ฉด ์ด๊ฒƒ์„ ๊ตฌ๋ถ„ํ•˜๊ธฐ ์œ„ํ•ด Hash Table์˜ ๊ธธ์ด๊ฐ€ ์ž‘์œผ๋ฉด ์ž‘์„์ˆ˜๋ก ์ด๋Ÿฌํ•œ ํ™•๋ฅ ์ด ์˜ฌ๋ผ๊ฐ„๋‹ค๋Š” ๋‹จ์ ์ด ์žˆ๋‹ต๋‹ˆ๋‹ค!

 

 

 

 

๐Ÿ“Œ ์ถฉ๋Œ(Collision)


ํ•ด์‰ฌ ํ…Œ์ด๋ธ”์˜ ๊ฐ€์žฅ ํฐ ๋ฌธ์ œ๋Š” ์ถฉ๋Œ์ธ ๊ฒƒ์ด์—์š”. ์ด ๋ฌธ์ œ๋ฅผ ์ถฉ๋Œ ๋˜๋Š” ํ•ด์‰ฌ ์ถฉ๋Œ(Hash Collision)์ด๋ผ ํ•œ๋‹ต๋‹ˆ๋‹ค!

 

    ๐Ÿ“ ์ถฉ๋Œ ํ•ด๊ฒฐ ์•Œ๊ณ ๋ฆฌ์ฆ˜

          ๐Ÿ‘‰ Chaning ๊ธฐ๋ฒ•

๊ฐœ๋ฐฉ ํ•ด์‹ฑ ํ˜น์€ Open Hashaing ๊ธฐ๋ฒ•์ด๋ผ๊ณ  ๋ถˆ๋ฆฌ๋Š” ๊ฒƒ์ด์—์š”. ์ด๊ฒƒ์€ ํ•ด์‰ฌ ํ…Œ์ด๋ธ” ์ €์žฅ ๊ณต๊ฐ„ ์™ธ ์ถ”๊ฐ€๋กœ ๊ณต๊ฐ„์„ ํ™œ์šฉํ•˜๋Š” ๊ธฐ๋ฒ•์ธ ๊ฒƒ์ด์—์š”.

์ถฉ๋Œ์ด ์ผ์–ด๋‚˜๋ฉด, ๋งํฌ๋“œ ๋ฆฌ์ŠคํŠธ๋ผ๋Š” ์ž๋ฃŒ ๊ตฌ์กฐ๋ฅผ ํ™œ์š”ํ•˜์—ฌ ๋งํฌ๋“œ ๋ฆฌ์ŠคํŠธ๋กœ ๋ฐ์ดํ„ฐ๋ฅผ ์ถ”๋ผ๊ณ  ๋’ค์— ์—ฐ๊ฒฐ ์‹œ์ผœ์„œ ์ €์žฅํ•˜๋Š” ๊ธฐ๋ฒ•์ธ ๊ฒƒ์ด๋ž๋‹ˆ๋‹ค.

 

CollisionChainning.py

 

# HashTable ์ถฉ๋Œ ํ•ด๊ฒฐ ํ•™์Šต

print("์—ฐ์Šต ๋ฌธ์ œ: ์—ฐ์Šต ๋ฌธ์ œ 1๋ฒˆ(hashTable.py)์˜ Hash Table Code์— Chaining ๊ธฐ๋ฒ•์œผ๋กœ ์ถฉ๋Œํ•ด๊ฒฐ Code ์ž‘์„ฑ")
print('-' * 100)
print("Hash Function : key % 8 \n Hash Key : hash(data)")
print('-' * 100 + '\n')

hash_table = list([0 for i in range(10)])


def hash_function(key_1):
    return key_1 % 10


def hash_key_maker(data1):
    return hash(data1)


def save_data(data1, value):
    # Hash Table์˜ ์ถฉ๋Œ๋กœ ์ธํ•˜์—ฌ ๋งํฌ๋“œ ๋ฆฌ์ŠคํŠธ๋ฅผ ํ†ตํ•˜์—ฌ chainning๊ธฐ๋ฒ•์„ ํ†ตํ•ด ํ•ด๊ฒฐ์„ ํ•˜๊ณ ์ž ํ•  ๋•Œ, ํ•ด๋‹น ๊ฐ’์„ ํŒ๋ณ„ํ•˜๊ธฐ ์œ„ํ•˜์—ฌ key๋ฅผ ๋”ฐ๋กœ ์ €์žฅ
    index_key = hash_key_maker(data1)

    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:
                hash_table[hash_address][index][1] = value
                return

        hash_table[hash_address].append(index_key, value)

    else:
        hash_table[hash_address] = [[index_key, value]]


def output_data(data1):
    index_key = hash_key_maker(data1)
    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

    return hash_table[hash_address]


# hash ์ถฉ๋Œ์„ ๋ฐœ์ƒ ์‹œํ‚ค๊ธฐ ์œ„ํ•ด Test
print(hash('Juny') % 10)
print(hash('Harang') % 10)
print(hash('Dev') % 10)
print('-' * 100 + '\n')

save_data('Juny', '12345678')
save_data('Dev', '22293848')

print(output_data('Juny'))
print('-' * 100 + '\n')

print(hash_table)
print('=' * 100 + '\n')

 

 

          ๐Ÿ‘‰ Linear Probing ๊ธฐ๋ฒ•

ํ์‡„ ํ•ด์Š ๋˜๋Š” Close Hashing ๊ธฐ๋ฒ• ์ค‘ ํ•˜๋‚˜๋กœ ํ•ด์‰ฌ ํ…Œ์ด๋ธ” ์ €์žฅ ๊ณต๊ฐ„ ์•ˆ์—์„œ ์ถฉ๋Œ ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ•˜๋Š” ๊ธฐ๋ฒ•์ธ ๊ฒƒ์ด์—์š”.

์ถฉ๋Œ์ด ์ผ์–ด๋‚˜๋ฉด, ํ•ด๋‹น hash address์˜ ๋‹ค์Œ address๋ถ€ํ„ฐ ๋งจ ์ฒ˜์Œ ๋‚˜์˜ค๋Š” ๋นˆ ๊ณต๊ฐ„์— Data๋ฅผ ์ €์žฅํ•˜๋Š” ๊ธฐ๋ฒ•์ด๋ž๋‹ˆ๋‹ค!
์ €์žฅ ๊ณต๊ฐ„ ํ™œ์šฉ๋„๋ฅผ ๋†’์ด๊ธฐ ์œ„ํ•ด์„œ ์‚ฌ์šฉํ•œ๋‹ค๊ณ  ํ•ด์š”!

 

 

CollisionLinearProbing.py

# HashTable ์ถฉ๋Œ ํ•ด๊ฒฐ ํ•™์Šต

print("์—ฐ์Šต ๋ฌธ์ œ: ์—ฐ์Šต ๋ฌธ์ œ 1๋ฒˆ(hashTable.py) Hash Table Code์— Linear Probing ๊ธฐ๋ฒ•์œผ๋กœ ์ถฉ๋Œ ํ•ด๊ฒฐ")
print('-' * 100)
print("Hash Function : key % 8 \n Hash Key : hash(data)")
print('-' * 100 + '\n')

hash_table = list([0 for i in range(10)])


def hash_function(key_1):
    return key_1 % 10


def hash_key_maker(data1):
    return hash(data1)


def save_data(data1, value):
    index_key = hash_key_maker(data1)
    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:
                hash_table[index] = [index_key, value]
                return

            elif hash_table[index][0] == index_key:  # ๊ฐ’์ด ๋‹ค๋ฅด์ง€๋งŒ, index Key๊ฐ€ ๋™์ผํ•˜๋‹ค๋ฉด?
                hash_table[index][1] = value  # ๊ทธ ๋‹ค์Œ ์œ„์น˜์— ๊ฐ’์„ ์ €์žฅํ•œ๋‹ค.
                return

    else:
        hash_table[hash_address] = [index_key, value]


def output_data(data1):
    index_key = hash_key_maker(data1)
    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:
                return None

            elif hash_table[index][0] == index_key:
                return hash_table[index][1]

    else:
        return None


print(hash('dk') % 10)
print(hash('da') % 10)

print('-' * 100 + '\n')


save_data('dk', '010393838')
save_data('da', '020393838')

print(output_data('dk'))
print(output_data('da'))
print('-' * 100 + '\n')

 

 

          ๐Ÿ‘‰ ๋นˆ๋ฒˆํ•œ ์ถฉ๋Œ์„ ๊ฐœ์„ ํ•˜๋Š” ๊ธฐ๋ฒ•

ํ•ด์‰ฌ ํ•จ์ˆ˜๋ฅผ ์žฌ์ •์˜ ํ•˜๊ฑฐ๋‚˜, ํ•ด์‰ฌ ํ…Œ์ด๋ธ” ์ €์žฅ ๊ณต๊ฐ„์„ ํ™•๋Œ€ํ•œ๋‹ค๋ฉด ์ถฉ๋Œ์˜ ๊ฐ€๋Šฅ์„ฑ์„ ๋‚ฎ์ถœ ์ˆ˜ ์žˆ๋Š” ๊ฒƒ์ด์—์š”.

์˜ˆ๋ฅผ ๋“ค์–ด 5๊ฐœ์˜ Data๋ฅผ ์ €์žฅํ•ด์•ผ ํ•œ๋‹ค๋ฉด 50%๊ฐ€ ๋„˜๋Š” ์ €์žฅ ๊ณต๊ฐ„์ธ 10๊ฐœ ์ด์ƒ์œผ๋กœ ํ•ด์‰ฌ ํ…Œ์ด๋ธ” ๊ณต๊ฐ„์„ ๋งŒ๋“œ๋Š” ๊ฒƒ์ด์ง€์š”!

 

๐Ÿ’ก์ฐธ๊ณ  : ํ•ด์‰ฌ ํ•จ์ˆ˜์™€ ํ‚ค ์ƒ์„ฑ ํ•จ์ˆ˜
               - Python์˜ hash()๋Š” ์‹คํ–‰ํ•  ๋•Œ๋งˆ๋‹ค, Value๊ฐ€ ๋‹ค๋ฅผ ์ˆ˜ ์žˆ๋‹ค.
               - ์œ ๋ช…ํ•œ Hash ํ•จ์ˆ˜ ์ข…๋ฅ˜ : SHA(Secure Hash Alogorithm, ์•ˆ์ „ํ•œ ํ•ด์‹œ ์•Œ๊ณ ๋ฆฌ์ฆ˜)
                  * ์–ด๋–ค Data๋„ ์œ ์ผํ•œ ๊ณ ์ • ํฌ๊ธฐ์˜ ๊ณ ์ •๊ฐ’์„ ๋ฐ˜ํ™˜ํ•ด์ฃผ๋ฏ€๋กœ, ํ•ด์‰ฌ ํ•จ์ˆ˜๋กœ ์œ ์šฉํ•˜๊ฒŒ ํ™œ์šฉ ๊ฐ€๋Šฅ

 

 

          ๐Ÿ‘‰ SHA-1

import hashlib

data = 'test'.encode()  # test String์„ Byte ํ˜•ํƒœ๋กœ ๋ฐ”๊ฟ”์ค€๋‹ค.
hash_obj = hashlib.sha1()
hash_obj.update(b'test')  # test String์„ Byte ํ˜•ํƒœ๋กœ ๋ฐ”๊ฟ”์ค€๋‹ค.

print('test์˜ sha1 ๊ฐ’์€ \'' + str(hash_obj) + '\' ์ž…๋‹ˆ๋‹ค.')
print('-' * 100 + '\n')

hex_dig = hash_obj.hexdigest()  # 16์ง„์ˆ˜๋กœ Byte ํ˜•ํƒœ๋กœ ๋ฐ”๊พผ ๊ฐ’์„ hex_dig์— ๋‹ด๋Š”๋‹ค.
print('test์˜ sha1์œผ๋กœ ๋ณ€ํ™˜ํ•œ ๊ฐ’์„ ๋‹ค์‹œ 16์ง„์ˆ˜๋กœ ๋ณ€ํ™˜ํ•œ ๊ฐ’์€ \'' + hex_dig + '\' ์ž…๋‹ˆ๋‹ค.')
print('-' * 100 + '\n')

 

 

          ๐Ÿ‘‰ SHA-256

import hashlib

data = 'test'.encode()  # test String์„ Byte ํ˜•ํƒœ๋กœ ๋ฐ”๊ฟ”์ค€๋‹ค.
hash_obj = hashlib.sha256()
hash_obj.update(b'test')  # test String์„ Byte ํ˜•ํƒœ๋กœ ๋ฐ”๊ฟ”์ค€๋‹ค.

print('test์˜ sha256 ๊ฐ’์€ \'' + str(hash_obj) + '\' ์ž…๋‹ˆ๋‹ค.')
print('-' * 100 + '\n')

hex_dig = hash_obj.hexdigest()  # 16์ง„์ˆ˜๋กœ Byte ํ˜•ํƒœ๋กœ ๋ฐ”๊พผ ๊ฐ’์„ hex_dig์— ๋‹ด๋Š”๋‹ค.
print('test์˜ sha256์œผ๋กœ ๋ณ€ํ™˜ํ•œ ๊ฐ’์„ ๋‹ค์‹œ 16์ง„์ˆ˜๋กœ ๋ณ€ํ™˜ํ•œ ๊ฐ’์€ \'' + hex_dig + '\' ์ž…๋‹ˆ๋‹ค.')
print('-' * 100 + '\n')


# HashTable ์ถฉ๋Œ ํ•ด๊ฒฐ ํ•™์Šต

print("์—ฐ์Šต ๋ฌธ์ œ: ์—ฐ์Šต ๋ฌธ์ œ 2๋ฒˆ(CollistionChainning.py)์˜ Chaining ๊ธฐ๋ฒ•์„ ์ ์šฉํ•œ Hash Table Code์— Key ์ƒ์„ฑ ํ• ์ˆ˜๋ฅผ SHA-256์œผ๋กœ ๋ณ€๊ฒฝ ํ•ด ๋ณด๊ธฐ")
print('-' * 100)
print("Hash Function : key % 8 \n Hash Key : hash(data)")
print('-' * 100 + '\n')

hash_table = list([0 for i in range(10)])


def hash_function(key_1):
    return key_1 % 10


def hash_key_maker(data1):
    hash_object = hashlib.sha256()
    hash_object.update(data1.encode())
    hex_digest = hash_object.hexdigest()

    return int(hex_digest, 16)  # ๋ฌธ์ž์—ด์ธ hex_digest๋Š” 16์ง„์ˆ˜๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋ฌธ์ž์—ด์ด ๋˜์–ด ์žˆ์œผ๋ฏ€๋กœ, ์ด๊ฒƒ์„ 10์ง„์ˆ˜ int๋กœ ๋ณ€ํ™˜ํ•œ๋‹ค.


def save_data(data1, value):
    # Hash Table์˜ ์ถฉ๋Œ๋กœ ์ธํ•˜์—ฌ ๋งํฌ๋“œ ๋ฆฌ์ŠคํŠธ๋ฅผ ํ†ตํ•˜์—ฌ chainning๊ธฐ๋ฒ•์„ ํ†ตํ•ด ํ•ด๊ฒฐ์„ ํ•˜๊ณ ์ž ํ•  ๋•Œ, ํ•ด๋‹น ๊ฐ’์„ ํŒ๋ณ„ํ•˜๊ธฐ ์œ„ํ•˜์—ฌ key๋ฅผ ๋”ฐ๋กœ ์ €์žฅ
    index_key = hash_key_maker(data1)

    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:
                hash_table[hash_address][index][1] = value
                return

        hash_table[hash_address].append(index_key, value)

    else:
        hash_table[hash_address] = [[index_key, value]]


def output_data(data1):
    index_key = hash_key_maker(data1)
    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

    return hash_table[hash_address]


# hash ์ถฉ๋Œ์„ ๋ฐœ์ƒ ์‹œํ‚ค๊ธฐ ์œ„ํ•ด Test
print(hash_key_maker('dbaa') % 10)
print(hash_key_maker('daaa') % 10)
print(hash_key_maker('dh') % 10)
print('-' * 100 + '\n')

save_data('dbaa', '12345678')
save_data('daaa', '22293848')

print(output_data('dbaa'))
print(output_data('daaa'))
print('-' * 100 + '\n')

print(hash_table)
print('=' * 100 + '\n')

 

 

 

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


์ผ๋ฐ˜์ ์ธ ๊ฒฝ์šฐ (Collision์ด ์—†๋‹ค๊ณ  ๊ฐ€์ •)๋Š” O(Big O)(1)์ด๊ณ , ์ตœ์•…์˜ ๊ฒฝ์šฐ(Collision์ด ๋ชจ๋‘ ๋ฐœ์ƒํ•˜์˜€์„ ๋•Œ๋ฅผ ๊ฐ€์ •)๋Š” O(n)์ด ๊ฑธ๋ฆฝ๋‹ˆ๋‹ค!

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

 

          ๐Ÿ‘‰ ๊ฒ€์ƒ‰์—์„œ Hash Table ์‚ฌ์šฉ ์˜ˆ

16๊ฐœ์˜ ๋ฐฐ์—ด์— Data๋ฅผ ์ €์žฅํ•˜๊ณ , ๊ฒ€์ƒ‰ํ•  ๋•Œ O(n)์ธ ๊ฒƒ์ด๊ณ , 16๊ฐœ์˜ Data ์ €์žฅ ๊ณต๊ฐ„์„ ๊ฐ€์ง„ ์œ„์˜ Hash Table์— Data๋ฅผ ์ €์žฅํ•˜๊ณ , ๊ฒ€์ƒ‰ํ•  ๋• O(1)์ด๋ž๋‹ˆ๋‹ค!

728x90
๋ฐ˜์‘ํ˜•