点击率预估分析中的问题
「Q:离线效果中AUC有提升,在线效果没有提升原因是什么?」
A:网上已经有很多的文章解释过这个问题,简单的说就是离线评估的 AUC 是评估请求与请求之间点击率的序,而在线评估的是广告与广告点击率的距,评估的角度就不一致,所以这种情况是有可能发生的。举一个极端的例子,假设人在 wifi 环境下更喜欢点广告,但无论是哪个广告更喜欢点的程度都是一样的,如果在离线环境下如果我们加入了是否在 wifi 环境下这个特征,我们就应该能得到更高的 AUC,而在线时,因为这个特征的影响对所有广告是一样的,其实无法提升我们的在线效果,因为 P(Ad_x|Wifi)=P(Ad_x),所以不会提升。
其实还有一个原因也很重要,我没有在网上见人提过,离线评估的结果更多的是反映的是曝光比较多的广告的效果,在广告系统中,广告的曝光量是长尾的,绝大部分广告只有比较少的曝光,当模型将曝光比较多的广告预测的比较好,而曝光比较少的广告预测的很差的时候,AUC 有可能是提升的,但在线时效果可能会很差,表现出来的现象是 Bias 比平均点击率偏高很多,原因是这些曝光比较少的广告可能把它们预测的偏低或是偏高,而只有偏高的时候才可能被观察到,那些偏低的没有曝光机会所以观察不到。之前遇到过这个问题,原因是我将广告 ID 采用 Hash 的方式去取 Embedding 向量,Embedding 矩阵行数我设置的比广告 ID 个数小很多,所以广告 ID 的冲突率是很高的,但从离线效果上看不出来,因为广告曝光数是长尾的,上线后效果很差。
「Q:我的在线实验 CPM 涨了,但 CTR 跌了应该如何处理?」
A:点击率预估优化的是收入,如果曝光没变,也可以理解为就是 CPM。CPM 是我们的优化目标,而 CTR 只是我们的指标,类似的还有转化率,负反馈率等等。最理想的情况当然是目标和指标都提升,但现实中如果不是 Bug fix 或是特别有效的特征,运气一般的情况下不会都提升。这种情况下经常有人问我是不是应该将两个,甚至多个目标一起进行优化,首先这样做无疑是很困难的,就一个优化目标经常都做不出来,不用说多个了,另外目标与目标之间如何衡量重要性,产品也只能给一个模糊的回答。
那么,如果 CTR 跌了,申请放量的时候就解释下为什么它可能是跌的,如果批实验放量的领导听不懂,就可以考虑离职了。如果听懂了,说 CTR 下降的比较大,可能对广告主带来一些困扰,那就应该在策略部分做些调整就可以了,也就是调整打分公式,比如加大 CTR 的影响,但请相信我,如果沦落到干这个,绝对是浪费生命,流量不停地在波动,这个值怎么也调不对,最后你能不能全量成功,全凭你放量的速度是不是够快。
「Q:我的曝光涨了,收入也涨了,但点击率和 CPM 都跌了,怎么处理呢?」
A:曝光涨了可能只在某些系统可能这样,比如 DSP,或是在线代码中会有一些阈值判断,比如 eCPM 没有达到一定的值不出广告这样的限制。举一个曝光涨了的例子,比如之前预测广告的 eCPM 偏低,现在预测的正常,就会多出一些广告,这时曝光就涨了。这里有一点比较难理解,多出来的那些曝光很可能是质量比较差的流量,所以如果实验点击率和 CPM 跌了,这很有可能是正常的,看收入更可信一些。我们对流量的效果进行比较的时候,需要两个流量的数据分布是近似的,如果曝光涨了,这个条件就不成立了,所以不可比。当然你要说服别人同意你放量,可能只凭假设不是够的,如果可以做到把阈值去掉,让实验的流量是可比的,也许更有说服力一些。
上面的情况是比较好的情况,但如果之前是预测偏高很多,现在预测正常了,因为曝光下降的原因,导致收入降低了很多,这种情况只能希望审批放量的同事是讲道理的,能结合阈值一起调。
「Q: 为什么我离线统计的 Bias 是正常的,但线上的 Bias 却高的离谱?」
A: 如果不是工程上的问题,出现的情况应该是高的离谱,如果低的离谱,还是先查下工程问题。先说下这里的 Bias 是什么,Bias=(pCTR-CTR)/CTR,比如 Bias 高达 20%,听上去是那么的不靠谱,但它却有可能是合理的,原因是模型无法做到那么的准确,它有可能预测偏高,也可能预测偏低,而预测偏低的情况下它很可能是无法获得曝光的,而预测偏高,特别是预测高的离谱的那些广告,它很可能会得到曝光机会,所以统计出来的 Bias 会明显偏高。
你如果是使用模型去预测,可能高 10-20% 是正常的,如果你用统计的方式去做,可能高 50%+都是正常的,如果你在解决新广告之类的问题,100%+ 都可能是正常的,当然这里的正常只是指的从算法的角度没有什么 Bug,但并不是说是一个合理的状态。
另外一点就是如果你看到一个模型预测的 AUC 蛮正常的,但 Bias 太高,可能先不要想着去对这个结果做一些调整,比如用另一个模型的结果进行修改,因为它本身可能就是合理的,你再修改下,可能更加的不靠谱。
「Q: 为什么我加入了更多其它来源的训练数据,效果反而更差了?」
A: 应该分两种情况讨论:
测试集(test set,不是 dev set 或 validate set)和训练集是同分布的,即也加入了更多其它来源的训练数据,这种情况下,一般来讲离线 AUC 效果会好很多,是由于训练数据中不同来源的数据有着较大的差异,比较好区分,但这时候的 AUC 评估是错误的,具体可以看下 Ng Andrew 的《Machine learning Yearning》中的 Your dev and test sets should come from the same distribution 一节中的介绍。这个错误有意思的地方在,如果知道这个问题,会无法理解有人竟然会犯这么简单的错误,而不知道的时候,犯这个错又是那么的自然。这个错在点击率中犯的可能性比较小,一般来讲是引入其它流量的数据,而且就算犯了这个错也比较好对比。然而最可怕的一种情况是从一开始就引入多来源的数据做,不停在模型上变来变去,一直做不出来。犯这种错最大的问题不是在于对机器学习或是业务的理解,而是处理问题的思路上,开始上线应该是数据特征算法做简化,也方便工程实现和 Bug 定位,做出一个可信的 base。
偏个题,其实在转化率预估中更容易犯这个错,转化的路径比如有点击->安装->激活->付费,如果能收集到所有转化数据,往往做的时候会把所有收集到的转化数据都用上,而不管广告主真的是想优化哪个目标(比如,安装),这种做法预测出来的值往往会特别离谱。
避免了第一个问题的情况下,离线效果一般不会有什么提升。
从特征的角度说,多个源的数据,特征不太可能都是一样的,那么一些源特有的特征在别的源上就是缺失特征,这样感觉更难学习。
从数据角度说,如果用多个源,其它源的数据量一定远大于原来的数据量(否则加进去的意义是什么呢?),那么训练时间一定大幅增加,时效性是否会对效果有影响?
从工程上不推荐这种做法,如果没有特别大的吸引力,建议就别用多个源的数据,因为多个源的数据来源可能来源于多个团队,每个团队都可能偶尔有工程问题,数据监控会很复杂,出了问题出错处理也会比较麻烦。