我使用python来解决一个学习排序问题,并使用以下DCG和NDCG代码(来自http://nbviewer.ipython.org/github/ogrisel/notebooks/blob/master/Learning%20to%20Rank.ipynb)来评估我的成功
def dcg(relevances, rank=20):
relevances = np.asarray(relevances)[:rank]
n_relevances = len(relevances)
if n_relevances == 0:
return 0.
discounts = np.log2(np.arange(n_relevances) + 2)
return np.sum(relevances / discounts)
def ndcg(relevances, rank=20):
best_dcg = dcg(sorted(relevances, reverse=True), rank)
if best_dcg == 0:
return 0.
return dcg(relevances, rank) / best_dcg
以下是最佳和最坏情况下的DCG值,在3个没有重复列组的项目列表中。。。在
^{pr2}$我们可以用这个指标来比较两个排名,看看哪个更好。但是,如果我计算一个4项列表的最坏情况。。。在
>>> ndcg(np.asarray([1,2,3,4]))
0.74890302967841715
4项清单似乎不再能与3项清单相媲美。在
我还计算了两个备选ndcg。NDCG2比较了所实现的dcg和bot的最佳和最坏情况。。。在
def ndcg2(relevances, rank=20):
best_dcg = dcg(sorted(relevances, reverse=True), rank)
worst_dcg=dcg(sorted(relevances, reverse=False),rank)
if best_dcg == 0:
return 0.
return (dcg(relevances, rank)-worst_dcg) / (best_dcg-worst_dcg)
NDCG将我的实际排名随机化50次,计算每个排名的dcg,并将其与我的实际dcg进行比较。在
def ndcg3(relevances, rank=20):
shuffled=np.copy(relevances)
rands=[]
for i in range(50):
np.random.shuffle(shuffled)
rands.append(dcg(shuffled,rank))
avg_rand_dcg=np.mean(np.asarray(rands))
return dcg(relevances, rank) / avg_rand_dcg
在我的各种列表中,我得到了以下指标。。。在
老实说,我对这些结果一无所知。我的NDCG值看起来不错,但它们真的可以在列表中进行比较吗?替代指标是否更有意义?在
编辑:在我的第一次随机比较中,我没有使用np.副本(). 因此,我的随机得分几乎总是0.99。现在这是固定的,结果更有意义。在
一种可能误导你的想法是将NDCG标准化。通常,您需要对多个文档进行排序,但是您的NDCG会在较少的文档数量上被截断(例如NCDG@3). 在您的代码中,这由参数“rank”决定。在
假设您想用R=[1,2,3,4,0]对5个文档进行排序,然后计算NDCG@3。如果您的算法认为最佳顺序是[doc1,doc2,doc3,doc4,doc5],那么您将得到:
而不是
^{pr2}$所以在某种意义上,NDCG([1,2,3])和NDCG([1,2,3,4])是不可比的。分子完全相同,但分母完全不同。如果你想让NDCG有一个直观的含义,你必须设置 “排名”小于或等于您的文档数。在
相关问题 更多 >
编程相关推荐