17位高级专家共同打造,涉及15个领域,133个体系框架,1000个细分知识点! 关注公众号大话数智,免费下载这份《数据智能知识地图》 导读:今天的主题是基于表征学习的因果推断技术实践。本次分享主要分为四大部分: 首先是工业界RCT实验规范,在工业界中,RCT数据对因果建模来说非常重要,但很多时候,我们对RCT数据的收集操作是不规范的,导致我们在建模时使用的是错误的数据,这将让我们在损失预算的情况下拉低线上效果,本文将会讨论一些RCT数据收集上的经验; 第二部分是树模型与深度模型的联合建模,树模型是工业界用到最多的模型,是很多公司的baseline模型,而深度模型也是一个主流趋势,它可以让我们自定义设计更灵活的网络结构,文中将讨论如何融合这两类模型,从而发挥二者优势; 第三部分是RCT数据和观测数据的融合建模,RCT数据虽然是无偏的,但是量少且贵,观测数据虽然有偏但是量大随处可得,所以我们希望通过RCT数据和观测数据融合建模,来提升数据量; 最后一部分是特征分解,它是目前比较热门学术研究方向,主要研究如何从特征里面去提取confounder,adjustmentvariable和IV。 全文目录:工业界RCT实验规范树模型NN联合建模RCTODB融合建模特征分解 分享嘉宾秦旋余珊珊快手增长算法工程师 编辑整理许振远腾讯 出品社区DataFun 01hr工业界RCT实验规范 首先对RCT数据做一个简单介绍。RCT为什么会有这么强大的魔力,为什么大家都在使用并且愿意投入大量的资金呢?主要原因有三点:ComparabilityandcovariatebalanceExchangeabilityNobackdoorpaths 1。Comparabilityandcovariatebalance 首先给出定义:如果协变量X的分布在任何Treatment组下都是一致的,我们就说wehavecovariatebalance。 用公式可以表达为: 即P(XT1)和P(XT0)是同分布的。 换句话说,几个treatment组中,除了treatment本身以外,其他的全部都一样。而随机(Randomization)可以帮助我们保证这一点。 下面是一个证明,假设population分布是P(X),在t1时,P(XT1)P(X);t0时,P(XT0)P(X),无论t等于任何值的情况下,分布都是一样的。 更重要的是,在RCT数据情况下可以导致因果就是关联。推导的过程如下图中所示。最重要的是第四个等号,当t和x独立时,P(tx)P(t),然后接一个全概率公式就能得到在do算子条件下的y就等于控制住t条件下的y,最终可以得到因果就是关联。这也是为什么我们在RCT数据上才能看到符合我们认知的数据现象。 2。Exchangeability 第二个是Exchangeability的成立,t和y的潜在结果是独立不相关的。因为除了t本身以外,其它的x变量都是一样的,拥有相同的性质,所以就算它们的treatment换过来,其潜在结果也不会发生任何变化,注意这里是潜在结果不会发生任何变化而不是结果本身,因为我们只能观察到一种结果。 3。Nobackdoorpaths 当我们拥有随机实验时,由于t跟x不再有关系,所以就没有了后门路径。 总结下来,RCT数据是一个黄金准则。因为它可以带来天然的非混淆性质,使得我们可以用这些数据去进行更好的建模。但不幸的是,随机数据极其昂贵,并且经常伴随着伦理问题。所以在大多数场景下,随机数据是一个奢饰品。但是在这种奢侈品有限的情况下,如何得到一个尽量无偏的估计呢?这里提供两个思路,第一个思路是在有限的预算下,尽量把RCT做正确、高效,因为只有保证这一点,才能才保证建模是对的;第二个思路就是在有偏的观测数据下找到无偏的部分,然后和RCT数据去融合建模。 如果不使用RCT数据建模会有什么后果呢?举个例子,我们可能会观察到戴眼镜的人学习成绩更好,进一步思考:戴眼镜本身是不是真的会影响学习成绩呢?答案显而易见,不会。因为如果戴眼镜可以提高学习成绩的话,大家都不需要去学习,直接去戴眼镜就好了。再进一步想就会发现学习时间长的人更容易戴眼镜,而学习时间长的人学习成绩更好,所以我们才会观测到戴眼镜会提高学习成绩这个假的因果效应,这就是学习时长这个confounder带来的混淆。如果简单地使用观测数据进行建模,那就会造成有偏的估计。因此需要RCT数据进行建模。 随机数据的弊端,如下图所列,不再赘述。因此,我们需要科学、高效的RCT方案。 工业界有两种不同的RCT设计方式:NestedDesign和NonNestedDesign。我们更希望得到的是NestedDesign,这也是用的最多的方式。当有一个目标population之后,直接从其中随机采样分成两组,一组作为RCT实验组,一组作为策略实验组。NonNestedDesign则采取了不同的采样机制,经常是在医学或者比较复杂的业务场景下退而求其次的选择。 如何设计我们的RCT方案呢? 首先要明确TargetPopulation,在做用户增长或者做因果推断时,明确目标人群是非常关键的一点,而往往也是容易被忽略的一点。因为有些时候,有些用户可能并不在做策略的人群里面,所以也就不必要出现在我们的RCT数据里面。因此,我们需要提前把RCT目标人群的集合缩小,只有精确到最小才能有一个高效的RCT实验。 举例来说,在我们做策略的时候,往往对于某些特定用户有着特殊的规则,并且这些规则往往是容易被人忽视的。例如某些有着特殊性质的用户,经常被给予一种或少数几种treatment。在进行RCT实验时,如果将这些人群加进来,就会导致各个treatment下的样本分布不均衡。 如果无法特别精确地定义targetpopulation,那么最简单的解决方法就是在线上服务的时候,做好日志记录,在每一次样本落表的时候,都有一个记录且仅记录一条实际的策略key,以便于进行正确的数据收取。但是最保险的方法还是要把targetpopulation精确到能力范围内最小。 第二,我们需要在实验前去shuffle流量,并且在实验中定期shuffle流量,这也是很容易被忽视的一步。很多团队的普遍做法是:在做RCT实验时,选择一个实验组,下掉之前的实验,然后直接在上面去做随机的策略。这就可能导致RCT组的分布和其他组的分布不一致。因为每个策略都会有各自长期带来的累积效应,如果累计时间长了特征无法AA实际上是不平的,用这样的数据训练出来的模型在另外一组上线可能会带来不好的效果。所以,定期shuffle流量是非常必要的一环。除此之外,RCT实验本身在广义上也是策略的一种,同样会对实验组样本分布造成很大的影响,所以定期shuffle流量或者每次都从wholepopulation中进行RCT数据的采样也是很重要的。 RCT实验的特征选取方法有两种:第一种是用户维度,第二种是请求维度。用户维度:一直给一个用户一个Treatment直到一个实验周期结束。请求维度:每次请求过来,系统随机给予一个Treatment。 具体使用哪种RCT,可以基于业务需要选择。比如用户维度的RCT可以帮助观察Treatment的累积效应。请求维度的RCT可以帮助我们看到单次Treatment带来的因果效应,并在相同预算下获得更多的训练样本。 但是无论选择哪一种都需要保证没有posttreatment特征。用户维度只能使用用户第一次请求前的特征,否则会造成特征穿越。请求维度只要是该请求前的特征都可以放心使用。 最后,介绍一个我们这边的主要做法:OnlineRCT。 相比于集中在某一个时间段开启一个大流量的RCT,持续在线的小流量RCT会更加经济有效。因为:它让我们永远都有与当前population分布相近的随机数据 当前,我们使用的RCT数据收集于2022年10月,然而,当我们使用这份数据训练出的模型对目前的策略数据进行预估时,不论是预估值的分布,还是Treatment分布,都与RCT数据的测试集有着较大的差距,OnlineRCT可以帮助我们缓解这一点。 使我们能更加灵活地变更treatment,避免浪费 之前,我们的RCT方式都是在一段时间内,大流量的开启RCT开关,一旦遇到treatment变更,就意味着我们之前的RCT实验数据不可用,造成时间和金钱的双重浪费。OnlineRCT可以有效的帮助我们缓解这一问题。它可以助力模型自动化更新 天级别的模型自动化更新功能已经应用在了很多场景下,也变成了一种趋势,但是,由于因果建模主要是使用RCT数据,所以如果没有高频率的数据更新,增量学习也就不现实了。OnlineRCT帮助我们解决了这一点。 当我们收集到RCT之后,还需要有一套完备的校验工具,主要用来检查数据的无偏性,这一步同样很重要,如果不能保证数据质量,后面所有的模型搭建或者训练可能都是有问题的。 02hr树模型NN联合建模 首先看一个很典型的因果图(见下图),U是未观测到的混淆变量,C是confounder,T是treatment,Y是outcome,A是adjustvariable,IV是工具变量。实际上,在工业界的因果图大多数情况下可以被简化成右边的图:未观测到的混淆变量没有了。在工业界很多场景下,可以假设没有未观测到的confounder。由于confounder都是训练线上模型时使用的特征,所以大多数情况下都是可知的。我们可以做一个假设:即我们的策略都是由模型决定的,模型里面用到的特征都是confounder。 在绝大多数公司里RCT建模的因果图中的C到T的边被取消了。 借助这张图,看下NN模型和树模型在建模因果效应时的不同方式。 下图是比较常见的DRNet,大多数情况下都是通过这样的损失函数去训练网络参数。但是它存在一个问题,如果我们去训练多头神经网络,每个头是对Y的回归,那么得到的Y是confounder和adjustmentvariable共同的表征。但是,实际上对因果效应造成影响的只有Confounder。因为网络并不是按照异质性建模,它只是一个回归模型,所以我们有可能把Y估计的很准。但是当我们去算因果效应时,在每一个头去减预测预估值时就会造成偏差。 举个例子,判断吃减肥药的效果。T是吃不吃减肥药,Y是体重,A是在量体重之前有没有上厕所,模型会给A一个参数,如果A的参数不一样时去相减算因果效应,就会带来误差,这些误差就会放大最后因果效应的估计。 RCT数据下,因果森林是基于异质性建模的,并且因果森林只在confounder上进行分裂,换而言之,它只会在为因果效应提供信息的特征上去进行分裂。在刚才的例子中,量体重之前是否上厕所在各个叶子节点内被消掉了,所以不会在A进行分裂。所以RCT因果森林输出的因果效应就是confounder的表征。 树模型可以得到confounder的表征,而NN可以支持更个性化的结构。在这里给出两种思路:思路1:使用树模型生成的confounderembedding作为NN模型的特征。思路2:使用对抗学习做特征分解。本文的第四部分会详细解释。 03hrRCTODB融合建模 首先,介绍一下PSmatching的方法,通过PS进行分层,在每一层内,通过计算spikedinestimator(分别计算每一层的ATE),得到该层内的causaleffect,最终加权得到总体的ATE。每个层下的O代表观测数据,R代表RCT数据,K是第K层。比如分k个桶,O(K)就是在观测数据里面的第K个桶,R是在RCT数据下第K个桶。 因果效应有一个比较成熟的思路:假设在任意一层tauoktaurk,对于每层的causaleffect,因果效应可以通过数据量的加权得到。这样一来,我们可以最终通过样本量加权得到总体ATE。该方法的优点是,可以解决PS在极值处样本量小的问题。此时小量RCT数据也可以较好地提升causaleffect的预估效果。这一套框架主要是想通过计算每一层的spikedinATE,然后加权得到群体的ATE,虽然这并不是我们想要的,但是我们可以借鉴该框架融入到我们的系统里。 市面上的观测数据和RCT融合主要是解决两部分问题,一部分是RCT数据分布和观测数据分布不一致,第二是观测数据有偏,我们现在解决的主要就是观测数据有偏的问题。 我们的做法主要分为三步:步骤一:分层,根据左侧图片,第一步是通过propensityscore对样本进行分层,一个好的PS模型并不需要精准的划分样本属于Treatment组或者Control组的能力,而是要具有covariatebalancing的能力。在这里,我们认为每一层的样本具有相同的性质。 步骤二:观测数据到RCT的covariateshifting,对观测数据采样,使得每层数据量和与之对应的RCT数据的数据量一致。这部分的目的是为了拉齐RCT与ODB的数据分布,在之前的工作中,我们的方法为在每一层内,RCT数据的样本数与ODB数据的样本数等比,通过这样的方式,可以使RCT和ODB中同性质样本等比,从而保证分布一致。 步骤三:观测数据unconfounding性质建立,该步骤是整套方法的核心。对同层内的Control组和Treatment组数据进行采样,对于每个层i,使得nobstinobscinrcttinrctci,以此来构造一个对不同性质的样本,被分到treatment组和被分到control组的概率等比。 我们还有一套验证机制来判断分层分的是否准确。简单来说,看观测数据和RCT数据的treatment组中的Y和因果效应在每一层内是否一致,如果不一致需要用RCT数据去填充。 随着对因果方向的深入,我们认为用GPS进行聚类不太合理。因为PropensityScoreVector并不是协变量X的表征,除了X,在对T进行回归的时候往往会无形的加入其他特征,那就是工具变量,所谓工具变量,就是不直接影响Y,只会通过影响T从而影响Y。如果在做分层的时候,使用的是包含IV的表示,那么会严重影响分层效果。举例来讲,补贴预算不会直接影响用户的活跃度,但是会通过影响用户得到激励的几率影响他的活跃度。如果将此类特征放到PS模型中,则在分层时会严重依赖该特征,反而影响其他X的balancing情况,所以我们必须想办法将这类特征过滤出去。有一篇论文论证了为什么IV会导致PropensityScoreInconsistency。 前文中提到了树模型的性质,只在confounder上进行分裂,得到的树模型输出的因果效应就是confounder的embedding。 下图中可以看到只有confounderX对因果效应提供了信息。如果把confounder作为聚类的特征,发现特征在每层内的协变量平衡效果会有非常大的增强。 下面是我们这套系统的几个模块:因果模型模块,该模块存在的目的是获得纯confounder的embedding。可嵌入任何模型,基于目前的认知,使用RCT数据和因果森林训练出的uplift是比较纯的confounderembedding。聚类模块,该模块存在的目的是基于confounder的embedding(输入自因果模型模块)获得准确的样本分层,在层内control组和Treatment组的分布一致,RCT数据和观测数据分布一致。covariateshifting模块,观测数据到RCT的covariateshifting。deconfounding模块,观测数据unconfounding性质建立。基于假设检验的校验模块,假设检验校验机制。评估系统,在一套系统中,评估机制是必不可少的,为此,我们开发了兼容所有stratification方法的评估系统,评估内容如下图。 04hr特征分解 前面介绍了基于RCT数据和观测数据融合建模的一些工作,可以看到,RCT样本难以构造且价格昂贵,所以我们尝试直接在观测样本上进行建模。在DNN建模中引入更多观测样本可以提升模型拟合效果和表达能力,但是引入观测样本的同时会引入bias。现有大部分工作都是通过样本ReweightingBalancing技术消除bias,经典的方法有:DragonNet、DML、特征分解等。 下面主要介绍特征分解的原始做法(参考发表在TKDE2022上的一个工作),以及我们落地时做的一些改进。基于因果图(右边的图)可以看到,协变量X分解成工具变量I,混淆变量和调整变量A,从而准确地分离出C和A去预估outcome(y),消除因为引入观测数据带来的bias。从图中可以看到工具变量I是只影响treatment,混淆变量C会影响treatment和outcome,调整变量A只会影响outcome。 论文中举了一个吃药的例子,treatment是吃不吃药,outcome是是否恢复健康。在病人的这些特征里面,收入和主治医生是工具变量,只会影响treatment;年龄和性别是混淆变量,会同时影响treatment和outcome,因为医生在选择treatment的时候会考虑病人的年龄和性别,而病人的年龄和性别也会影响恢复健康的概率;基因和环境是调整变量,只会影响outcome。 要准确地将协变量X分解为三个不同类型的隐变量,做法如下:首先从X中分解A,需要满足以下两个条件:一个是调整变量A和T独立,目的是约束其他变量的信息不会嵌入到调整变量A中。因为从因果图上可以看到,工具变量I和混淆变量C跟T之间是有关系的;另一个是调整变量A能够尽可能精准地预估Y,从而保证A的信息不会嵌入到其他变量中。然后是从X中分解I,如果balancing做得好,C和T之间将没有依赖,那么在给定的情况下I和Y独立。这是因为做好不同treatment下confounder的平衡后,C和T之间的因果效应被去掉了,当给定T时,I和C、I和Y之间都是独立的,从而保证其他变量的信息不会嵌入到工具变量I中。同时I需要尽可能精准地预估T,保证I的信息不会嵌入到其他变量中。最后基于分解后的C和A去预估事实和反事实结果。 基于上述分析,设计了以下几个loss来分解协变量X:首先分解A,通过最小化不同treatment下的分布差异实现(),同时最小化基于预估的损失。disc()表示不同treatment下分布的差异,可以用IPM、MMD、Wassersteindistance等度量函数来衡量。其次通过balancing不同treatment下的分布去掉C和之间的依赖,实现()。为可学习参数,是样本层面的一个加权。然后通过最小化不同treatment下分布的差异实现,同时最小化基于预估的损失。同样这里也在样本层面利用进行了加权。 除了上述几个loss之外,为了避免过拟合和分解不干净,论文中还增加了正交正则化来改进效果。以为例,认为权重矩阵表示输入中的每个变量对输出()的贡献。和同理。所以如果协变量能够充分分解成I,,A,这些权重矩阵应该是正交的。此外为了防止学出来的权重都是零,约束各维权重和为1。 以上就是论文中给出的特征分解的做法,在我们落地的过程中对其做了一些优化。首先论文中主要是针对01treatment的情况,我们将它升级为多treatment,并且引入多头结构,每个treatment生成对应的I,,A表征。其次在平衡confounder的步骤中,使用IPW替代可学习参数来平衡样本。对于多treatment,基于的表征预估treatment,从而得到对应的权重。最后引入对抗loss来保证变量之间独立。 论文中是通过最小化不同treatment下的分布差异来保证变量之间独立,基于欧式距离、cosine距离以及mmd等度量函数来衡量分布差异的大小。我们的目标是变量之间无关,不包含有用的信息量,用不同treatment下分布相似来表达和treatment无关不够直观。此外,分布相似度度量函数计算量比较大,在大规模样本且多treatment的情况下需要大量的计算资源。因此我们尝试从信息的角度考虑,通过约束()中不存在信息可以去预估来保证A和T独立。 基于这个想法,我们引入对抗loss,目标是让A(X)无法准确预估T,即对于多treatment,预估概率都是1n,n是treatment的个数。首先使用预训练网络作为判别器,固定A的表示,更新判别器参数,使其尽可能准确地预估T。然后固定判别器,更新A的表示,使其尽可能准确地预估fakelabel(1n)。循环训练,直至达到目标。此时A中不存在信息可以预估T,达到A和T独立的目的。 以上就是本次分享的全部内容。 最后,欢迎对因果推断感兴趣或者有经验的人才加入我们,谢谢大家! 05hr问答环节 Q1:基于观测数据做debias,需要同时考虑模型的相关性和debias的效果,在这种情况下,如何在有限的数据中进行离线评估? A1:这个是一个很好的问题,我们基于观测数据去做建模的时候,或者在对观测数据进行去偏的时,经常需要去看看debias的效果。如果没有RCT数据,我们的做法是,对样本在propensityscore上做分层,如果每一层底下样本是同质的,就可以观察到treatment组和control组的比例就是全量样本中treatment组和control组的比例。在这种情况下,就说明debias做的不错。 Q2:用户维度的RCT不断有新用户涌入是否会导致通不过AA校验? A2:不论是用户维度还是请求维度,新用户进来的时候也是随机的会被划分到某一个组。用户落在每一个组里面的概率是相等的。如果每个用户落在每一个组的概率相等的,就不会造成treatment组之间AA特征的变化。 Q3:长期的onlineRCT是否会违反用户的公平性原则或者带来潜在的RCT问题? A3:需要我们在设计RCT的时候考虑到这一点,如果你的业务容易造成这样的PR问题,需要在设计RCT的时候想好应对方法。如果是业务本身风险性就较高,那可能RCT本身就不是一个可以去上线的策略了。 Q4:关于长期onlineRCT怎么做模型效果评估?分享中提到用户粒度的特征只能用treatment之前的,长期onlineRCT怎么做? A4:做法和上文提到的特征构建方式相同。 Q5:关于表征学习学习出来的Wi和倾向性得分可以具体对应上吗? A5:使用倾向性得分IPW去代替w,出发点是因为整体loss设计已经比较复杂了,可以看到针对各个分解的变量设计了不同的loss,如果最终还要去学参数w,从实践来看是比较难学习的。而IPW比较成熟,在我们落地过程中也被验证过,效果是比较好的。 今天的分享就到这里,谢谢大家。 分享嘉宾 秦旋快手增长算法工程师 毕业于美国波士顿大学,清华大学计算机系研究员。曾在滴滴出行任职高级算法工程师,研究方向为因果推断。曾自主开发了一套适用于工业界的RCT观测数据融合算法。参与开发基于SPARK的分布式因果森林,并进行改造与升级。该工作在网约车智能定价业务上多次取得ROI收益。加入快手后,负责裂变场景下RCT数据流的规范化开发与树模型深度模型的联合建模。 余珊珊快手增长算法工程师 浙大硕士,2020年加入快手,现主要工作内容为基于表征学习的因果推断方法在裂变场景的业务落地和技术创新。 DataFun新媒体矩阵 关于DataFun 专注于大数据、人工智能技术应用的分享与交流。发起于2017年,在北京、上海、深圳、杭州等城市举办超过100线下和100线上沙龙、论坛及峰会,已邀请超过2000位专家和学者参与分享。其公众号DataFunTalk累计生产原创文章900,百万阅读,近16万精准粉丝。