从多样性谈起到dpp

在推荐算法中,除了要考虑个性化,还要兼顾多样性,不然用户很快就会觉得单调无趣。
在衡量推荐结果的多样性时,自然而然能想到的是统计推荐结果中含有不同tag的个数,tag的个数越多,多样性越好。但是这种指标有个问题,它与用户看的内容条数正相关,用户看的内容条数越多,自然tag个数会越多。假设一条feed平均有3个tag,只看了1条feed用户的多样性指标是3;看了10条feed的用户,总共有30个 tag,假设有50%的重合度,有15个不同tag,大大高于看了1条feed的用户。
为了抵消feed条数的影响,于是有人又想到了用不同tag个数/feed条数。这样乍看起来比较合理,但其实又会与feed条数负相关了。还是以上面的例子来计算,看了1条feed的用户,多样性指标是3/1=3; 看了10条feed的用户,多样性指标是15/10=1.5,低于看了1条feed的用户。只要看过的多条feed之间有重复的tag,多样性指标就会低于只看了1条feed的用户。
以上两种指标都与用户的行为条数相关,都不是稳定的指标。下面介绍一个稳定的指标,用feed两两之间不同tag个数的总和/feed两两组合个数,代码如下:

def compute_diversity(item_list, item_cate_map):
    n = len(item_list)
    diversity = 0.0
    for i in range(n):
        for j in range(i+1, n):
            diversity += item_cate_map[item_list[i]] != item_cate_map[item_list[j]]
    diversity /= ((n-1) * n / 2)
    return diversity

这个指标基本与用户的行为条数无关了,因此是稳定的。
但上面的指标也有个问题,就是过度依赖feed的tag。tag描述有两个问题:一是无法全面表示feed内容,另外是tag的粗细粒度不一致,比如汽车和宝马都是tag,但他们的描述范围差别很大。我们知道,embedding向量可以用来表示feed,而且粒度相对一致。那么可不可以用embeding代替tag来计算多样性呢,答案是肯定的。
用fi表示feedi的embedding;用<fi,fj>表示两个embedding的点积,点积代表两个向量的相似度;用1-<fi,fj>表示两个向量的差异性,即两个feed之间的差别程度。参考上面tag的方式,可以用如下公式来计算feed列表的多样性:
∑ i = 0 n ∑ j = i + 1 n 1 − f i ⋅ f j ( n − 1 ) ∗ n / 2 \frac{\sum_{i=0}^n\sum_{j=i+1}^n1-f_i\cdot f_j}{(n-1)*n/2} (n1)n/2i=0nj=i+1n1fifj
这个公式有点不完美的是只考虑了两个feed之间的差别,没有考虑多个feed之间的整体差别,举个极端点的例子:假设第一组3个feed,A与B的点积为1,C与A、B的点积都为0,用上面公式计算这3个feed的多样性为(0+1+1)/3=2/3; 第二组3个feed,A、B、C之间的点积都为0.5,多样性为(0.5+0.5+0.5)/3=0.5; 单纯从指标上来看,第一组的多样性要高于第二组。但实际上第二组的多样性更好,因为第一组feed A与B完全一样, 第二组3个feed两两之间的差别比较均匀。
那么有没有更好的方式来计算feed列表的多样性呢。我们知道feed embedding是一个向量,向量之间的夹角代表feed的差别大小,夹角越大差别越大。那么我们可以用列表中所有feed embedding向量撑起的多维体的体积来表示整个列表的多样性,体积越大多样性越好,这既考虑了feed两两之间的差别,也考虑到了整体差别的均匀性,不会因为某两个feed差别过大而忽略了其他feed的差别。

下面介绍怎么计算体积,定义矩阵L, L i j = f i ⋅ f j = r i r j cos ⁡ α i j L_{ij}=f_i\cdot f_j=r_ir_j\cos\alpha_{ij} Lij=fifj=rirjcosαij,表示feed embedding两两之间的点积,其中r表示feed embedding向量的长度,归一化的embedding向量长度一般为1; α i j \alpha_{ij} αij表示两个feed之间的夹角,矩阵的格式如下:
[ f 1 ⋅ f 1 f 1 ⋅ f 2 ⋯ f 1 ⋅ f n f 2 ⋅ f 1 f 2 ⋅ f 2 ⋯ f 2 ⋅ f n ⋮ ⋮ ⋱ ⋮ f n ⋅ f 1 f n ⋅ f 2 ⋯ f n ⋅ f n ] = [ r 1 2 r 1 r 2 cos ⁡ α 1 , 2 ⋯ r 1 r n cos ⁡ α 1 , n r 1 r 2 cos ⁡ α 1 , 2 r 2 2 ⋯ r 2 r n cos ⁡ α 2 , n ⋮ ⋮ ⋱ ⋮ r 1 r n cos ⁡ α 1 , n r 2 r n cos ⁡ α 2 , n ⋯ r n 2 ] \begin{bmatrix} f_1\cdot f_1&f_1\cdot f_2&\cdots&f_1\cdot f_n\\ f_2\cdot f_1&f_2\cdot f_2&\cdots&f_2\cdot f_n\\ \vdots&\vdots&\ddots&\vdots\\ f_n\cdot f_1&f_n\cdot f_2&\cdots&f_n\cdot f_n\\ \end{bmatrix}= \begin{bmatrix} r_1^2&r_1r_2\cos\alpha_{1,2}&\cdots&r_1r_n\cos\alpha_{1,n}\\ r_1r_2\cos\alpha_{1,2}&r_2^2&\cdots&r_2r_n\cos\alpha_{2,n}\\ \vdots&\vdots&\ddots&\vdots\\ r_1r_n\cos\alpha_{1,n}&r_2r_n\cos\alpha_{2,n}&\cdots&r_n^2\\ \end{bmatrix} f1f1f2f1fnf1f1f2f2f2fnf2f1fnf2fnfnfn=r12r1r2cosα1,2r1rncosα1,nr1r2cosα1,2r22r2rncosα2,nr1rncosα1,nr2rncosα2,nrn2
先下结论矩阵L的行列式|L|即为多维体体积的平方。
先看两维的情况:
∣ r 1 2 r 1 r 2 cos ⁡ α 1 , 2 r 1 r 2 cos ⁡ α 1 , 2 r 2 2 ∣ = r 1 2 r 2 2 ( 1 − cos ⁡ 2 α 1 , 2 ) = ( r 1 r 2 sin ⁡ α 1 , 2 ) 2 \left|\begin{matrix} r_1^2&r_1r_2\cos\alpha_{1,2}\\ r_1r_2\cos\alpha_{1,2}&r_2^2\\ \end{matrix}\right|= r_1^2r_2^2(1-\cos^2\alpha_{1,2})= (r_1r_2\sin\alpha_{1,2})^2 r12r1r2cosα1,2r1r2cosα1,2r22=r12r22(1cos2α1,2)=(r1r2sinα1,2)2,
这正好是f1、f2两个embedding向量组成的平行四面体的面积平方值。
在这里插入图片描述

再看三维的情况:
∣ r 1 2 r 1 r 2 cos ⁡ α 1 , 2 r 1 r 3 cos ⁡ α 1 , 3 r 1 r 2 cos ⁡ α 1 , 2 r 2 2 r 2 r 3 cos ⁡ α 2 , 3 r 1 r 3 cos ⁡ α 1 , 3 r 2 r 3 cos ⁡ α 2 , 3 r 3 2 ∣ = r 1 2 r 2 2 r 3 2 ( 1 + 2 cos ⁡ α 1 , 2 cos ⁡ α 1 , 3 cos ⁡ α 2 , 3 − cos ⁡ 2 α 1 , 2 − cos ⁡ 2 α 1 , 3 − cos ⁡ 2 α 2 , 3 ) \left|\begin{matrix} r_1^2&r_1r_2\cos\alpha_{1,2}&r_1r_3\cos\alpha_{1,3}\\ r_1r_2\cos\alpha_{1,2}&r_2^2&r_2r_3\cos\alpha_{2,3}\\ r_1r_3\cos\alpha_{1,3}&r_2r_3\cos\alpha_{2,3}&r_3^2\\ \end{matrix}\right|= r_1^2r_2^2r_3^2(1+2\cos\alpha_{1,2}\cos\alpha_{1,3}\cos\alpha_{2,3}-\cos^2\alpha_{1,2}-\cos^2\alpha_{1,3}-\cos^2\alpha_{2,3}) r12r1r2cosα1,2r1r3cosα1,3r1r2cosα1,2r22r2r3cosα2,3r1r3cosα1,3r2r3cosα2,3r32=r12r22r32(1+2cosα1,2cosα1,3cosα2,3cos2α1,2cos2α1,3cos2α2,3)
这正好是f1、f2、f3三个embedding向量组成的平行六面体的体积平方值

依此类推,n维矩阵L的行列式为f1、f2、···、fn组成的多维体的体积平方值。
至此,我们可以用列表中feed embedding向量两两之间的点积组成矩阵L,然后计算L的行列式值表示该列表的多样性。这种方式可以比较完美的衡量一个feed列表的多样性。
在推荐算法中还有一种应用场景,就是在排序后的m个feed中选出k(k<m)个feed,使这k个feed的排序分尽量高,同时多样性最大化。这时不能只考虑多样性了,还要兼顾排序分。我们可以改造一下上面的矩阵L,使 L i j = s i s j f i ⋅ f j = s i s j r i r j cos ⁡ α i j L_{ij}=s_is_jf_i\cdot f_j=s_is_jr_ir_j\cos\alpha_{ij} Lij=sisjfifj=sisjrirjcosαij,其中s表示feed的排序分,也就是使原来feed embedding向量长度伸缩s倍。伸缩后的向量组成的多维体体积越大,即边长(排序分)尽量大的同时,夹角(多样性)也要尽量大,这样同时兼顾了排序分和多样性。这即是著名的dpp算法了。
在实际使用中,还可以修改一下矩阵L,使 L i j = w s i s j f i ⋅ f j L_{ij}=ws_is_jf_i\cdot f_j Lij=wsisjfifj,通过修改w来调节排序分与多样性之间的权重,使结果更偏重于排序还是多样性。对不同的用户用不同的w,即可以实现多样性的个性化。对不同排序模型用不同的w来消除不同排序模型对dpp的bias影响。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值