python手刃lintcode(128) :哈希函數【簡單題】

python手刃lintcode(128) :哈希函數【簡單題】

這道題沒有什麼算法難點,公式已經給出了,重點是一些函數的使用和時間複雜度的問題。python

字符串轉換函數:算法

  • ord(c):參數是長度爲1的字符串,簡稱字符。當參數爲統一對象時(unicode object),返回能表明該字符的統一編碼,當參數爲8比特的字符串時,返回該字節的值。例如,ord('a')返回整形數值97,ord(u'\u2020')返回8224。
  • chr(i):返回一個字符,字符的ascii碼等於參數中的整形數值。例如chr(97)返回字符'a',該方法是ord()的反方法。參數必須是0-255的整形數值,不然會拋出valueError錯誤。

注意這裏不能用int() 函數進行轉化,由於該函數的輸入值只是時數字。函數

class Solution:
    """ @param key: A string you should hash @param HASH_SIZE: An integer @return: An integer """
    def hashCode(self, key, HASH_SIZE):
        # write your code here
        n = len(key)
        num = 0
        for i in range(n):
            num += ord(key[i])*(33**(n-i-1))
        num = num % HASH_SIZE
        return num
複製代碼

可是上邊這個程序會報超時的錯誤,接下來考慮怎麼下降時間複雜度。由於自己的轉換公式已經給定了,因此能下降複雜度的方法也就是從計算順序等方面着手。編碼

下降時間複雜度方法:spa

  1. 若是從前日後順次轉化,那麼能夠發現要從 33^{n-1} 算到 33^{0} ,即須要計算n(n-1)/2 次,因此咱們能夠改變一下順序,從後往前進行轉換,並保留每次計算的33次方的值,在下一次計算時再乘以33便可,這樣只須要計算 n-1 次便可,能夠下降時間複雜度。
  2. 對於轉換公式:

hashcode(「abcd」) = (ascii(a) * 333 + ascii(b) * 332 + ascii(c) *33 + ascii(d)) % HASH_SIZEcode

來講,其實徹底能夠對每一項先取餘再相加(能除就儘可能先除),這樣能夠減小內存佔用和計算量。對象

改進後的程序:內存

class Solution:
    """ @param key: A string you should hash @param HASH_SIZE: An integer @return: An integer """
    def hashCode(self, key, HASH_SIZE):
        # write your code here
        n = len(key)
        num = 0
        temp = 1
        for i in range(n-1,-1,-1):
            num += ord(key[i])*temp%HASH_SIZE   
            temp = temp*33 % HASH_SIZE
        num = num % HASH_SIZE
        return num
複製代碼
相關文章
相關標籤/搜索