2012-05-08 13 views
1

我正在建立一個音樂推薦引擎,它使用音軌的歌詞來找出歌曲在情感上與彼此的緊密聯繫。我使用了tfidf算法(這裏沒有顯示)爲每首歌曲生成一個分數,並且我想將每個音軌的tfidf分數存儲在名爲tfidf的django模型字段中。但是我想按照0-1的比例規範每個tfidf分數。你如何編寫一個可以自動標準化數據的django模型?

我遇到的困難是如何在有人在管理界面中輸入tfidf值時自動規範這些tfidf分數。所以想象一下,你已經進入了管理界面,並希望將歌曲「In Da Club」添加到數據庫中。您在歌曲的名稱和它的TFIDF分數,像這樣類型:

enter image description here

我希望做的是確保一旦你打保存按鈕,它會自動填充空normalized_tfidf列與規範化的價值。我正在使用一個簡單的算法來標準化tfidf值。在我進入它之前,讓我告訴你這張桌子是什麼樣子的,這樣你就可以更清楚地瞭解算法在做什麼。於是,經過「在大俱樂部」已被添加到數據庫中(和數據已經標準化),表列應該是這個樣子:

enter image description here

宋x和歌y是隻是虛擬的歌曲我已經將數據庫植入了數據庫,爲算法設置了一個上限和下限。您看到的.50077的值就是我想要自動生成的值。

該算法表示要找到歌曲x中的特徵tfidf的歸一化值(nv),找出歌曲的tfidf得分與表中最小的tfidf得分之間的差異,並將該差異除以最大值與最小值表中最小tfidf分數。這在數學上是。

NV(在大俱樂部TFIDF)=在大俱樂部TFIDF - TFIDF 分鐘/TFIDF 最大 - TFIDF 分鐘

而這裏的計算:

NV(在da俱樂部)= .25048 - .00010/.50000 - .00010 = .50077

所以我試圖將其編碼到我的模型中。問題在於,django似乎沒有方法讓我可以用SQL語句的方式在表中選擇最小和最大tfidf值。我對django相當陌生,並沒有完全意識到它的能力。如果我的表格模型看起來像我下面的模型,那麼重寫它的最好方法是什麼,以便tfidf在您輸入管理員後自動進行標準化?

enter image description here

回答

1

有兩種方式來觸發,當一個模型保存一些行動:重寫save方法,或者寫一個post_save聽衆。我會顯示重寫方法,因爲它更簡單一些,並且很好地適合這個用例。

爲了獲得最大/最小值,你可以使用Django的queryset aggregation functions

from django.db.models import Max, Min 


class Party(models.Model): 
    ... 
    def save(self, *args, **kwargs): 
     max = Party.objects.all().aggregate(Max('tfidf'))['tfidf__max'] 
     min = Party.objects.all().aggregate(Min('tfidf'))['tfidf__min'] 
     self.normalized_tfidf = (self.tfidf - min)/(max - min) 
     super(Party, self).save(*args, **kwargs) 

重寫像save默認模型方法是非常簡單的,但是有一些更多信息here如果你有興趣。

請注意,如果您在任何時候在做bulk updatesParty.tfidf,保存處理程序將不會被調用(或者發送post_save信號),所以您必須手動處理所有行 - 哪些將意味着很多數據庫寫入,並且會使大量更新毫無意義。

+0

感謝您的有益迴應。然而,當我嘗試運行dev服務器時,我得到以下錯誤...不知道是什麼導致它:文件「/Users/mikaschiller/Documents/djangoprojects/twizzle/models.py」,第35行 min = Party.objects .all()。aggregate(Min('tfidf')['tfidf__min'] ^ SyntaxError:無效的語法 –

+0

看起來像缺少')'。應該是Party.objects.all()。aggregate(Min('tfidf'))['tfidf__min'] - 我看到我也錯過了我的答案。現在編輯... –

相關問題