使用机器学习排序算法LambdaMART有一段时间了,但一直没有真正弄清楚算法中的全部细节。html
学习过程当中细读了两篇不错的博文,推荐给你们:算法
徐博From RankNet to LambdaRank to LambdaMART: An Overviewiphone
但通过一番搜寻以后发现,目前网上并无一篇透彻讲解该算法的文章,因此但愿这篇文章可以达到此目的。机器学习
本文主要参考微软研究院2010年发表的文章From RankNet to LambdaRank to LambdaMART: An Overview11,并结合本身的理解,试图将RankNet、LambdaRank和LambdaMART这三种算法的全部算法细节讲解透彻。函数
RankNet、LambdaRank和LambdaMART是三个关系很是紧密的机器学习排序算法。简而言之,RankNet是最基础,基于神经网络的排序算法;而LambdaRank在RankNet的基础上修改了梯度的计算方式,也即加入了lambda梯度;LambdaMART结合了lambda梯度和MART(另称为GBDT,梯度提高树)。这三种算法在工业界中应用普遍,在BAT等国内大厂和微软谷歌等世界互联网巨头内部都有大量应用,还曾经赢得“Yahoo!Learning To Rank Challenge(Track 1)"的冠军。本人认为若是评选当今工业界中三种最重要的机器学习算法,以LambdaMART为表明的集成学习算法确定占有一席之地,另外两个分别是支持向量机和深度学习。学习
2.1 算法基础定义优化
RankNet解决以下搜索排序问题:给定query集合,每一个query都对应着一个文档集合,如何对每一个query返回排序后的文档集合。能够想象这样的场景:某位高考生在得知本身的成绩后,准备报考志愿。据说最近西湖大学办得不错,因此就想到网上搜搜关于西湖大学的资料。他打开一个搜索引擎,输入“西湖大学”四个字,而后点击“搜索”,页面从上到下显示了10条搜索结果,他认为排在上面的确定比下面的相关,因此就开始从上往下一个个地浏览。因此RankNet的目标就是对全部query,都能将其返回的文档按照相关性进行排序。搜索引擎
RankNet网络将输入query的特征向量x∈Rnx∈Rn映射为一个实数f(x)∈Rf(x)∈R。RankNet采用pairwise的方法进行模型训练。具体地,给定特定query下的两个文档UiUi和UjUj,其特征向量分别为xixi和xjxj,通过RankNet进行前向计算获得对应的分数为si=f(xi)si=f(xi)和sj=f(xj)sj=f(xj)。用Ui⊳UjUi⊳Uj表示UiUi比UjUj排序更靠前(如对某个query来讲,UiUi被标记为“good”,UjUj被标记为“bad”)。继而能够用下面的公式来表示UiUi应该比UjUj排序更靠前的几率:atom
这个几率实际上就是深度学习中常用的sigmoid函数,参数σσ决定sigmoid函数的形状。对于特定的query,定义Sij∈{0,±1}Sij∈{0,±1}为文档ii和文档jj被标记的标签之间的关联,即
定义P¯¯¯¯ij=12(1+Sij)P¯ij=12(1+Sij)表示UiUi应该比UjUj排序更靠前的已知几率,则能够用交叉熵定义优化目标的损失函数:
若是不太熟悉什么是交叉熵,能够参考宗成庆老师的《统计天然语言处理》2.2节“信息论基本概念”,里面将熵、联合熵、互信息、相对熵、交叉熵和困惑度等概念都讲得至关清楚。
结合以上多个公式,能够改写损失函数CC为:
对于Sij=1Sij=1,
然而对于Sij=−1Sij=−1,
能够看出损失函数CC具备对称性,也即交换ii和jj的位置,损失函数的值不变。
分析损失函数CC的趋势发现,若是对文档UiUi和UjUj的打分能够正确地拟合标记的标签,则CC趋向于0,不然CC趋向于线性函数。具体地,假如Sij=1Sij=1,也即UiUi应该比UjUj排序高,若是si>sjsi>sj,则拟合的分数能够正确排序文档ii和文档jj,
若是si<sjsi<sj,则拟合的分数不能正确排序文档ii和文档jj,
利用神经网络对模型进行训练,目前最有效的方法就是反向传播算法。反向传播算法中最核心部分就是损失函数对模型参数的求导,而后可使用下面的公式对模型参数进行迭代更新:
损失函数CC对sisi和sjsj的偏导数为:
sisi和sjsj对wkwk的偏导数可根据神经网络求偏导数的方式求得。求得了损失函数CC对神经网络模型参数wkwk的偏导数以后,就可使用梯度降低算法对其更新。这里的学习率ηη也是一个正数,由于ηη须要知足下面的不等式:
2.2 RankNet分解形式:加速RankNet训练过程
2.1节中定义的RankNet,对于每个文档对(Ui(Ui,Uj)Uj)都将计算损失函数对神经网络的参数wkwk的偏导数,而后更新模型参数wkwk。这样作的缺点在于,对模型参数更新慢,耗时长。因此本节讲解如何经过分解组合的方式加快这一训练过程。
对于给定的文档对UiUi和UjUj,损失函数CC对参数wkwk的偏导数为:
其中:
定义II为索引对{i,j}{i,j}的集合,在不损失信息量的状况下,能够将集合II中的索引对都转换成知足Ui⊳UjUi⊳Uj的形式。另外集合II中的索引对还应该知足最多只出现一次的条件。在此基础上,累加权重参数wkwk的更新量:
其中:
通俗地说,λiλi就是集合II中全部{i,j}{i,j}的λijλij的和−−集合II中全部{j,i}{j,i}的λijλij的和。若是仍是不太明白,那看下面这个例子就明白了。集合I={{1,2},{2,3},{1,3}}I={{1,2},{2,3},{1,3}},则