(轉載請注明原創於潘多拉盒子)
算法效果的AB測試,是指在相同的應用場景下,對比不同算法的效果。通常的做法是,按照PV或UV隨機分配流量到算法上,計算算法的CTR或轉化率進行對比。為了表述簡單,我們假設參與對比的算法有兩個,比較的指標是CTR。這里面的關鍵細節有兩個:1. 如何划分瀏覽?2. 如何計算CTR。下面從這兩個角度討論可能出現的問題。
定義1:按PV划分流量,是指對任意一個訪問,按照預先設定的比例,隨機分配到一個算法中。需要注意的是,在這種情況下,每個用戶會被隨機分配到一個算法中。
定義2:按UV划分流量,是指對任意一個訪問,按照預先設定的比例,對用戶ID進行哈希和取模等操作,將流量划分到一個算法中。在這種情況下,每個用戶有一個確定的算法與之對應。
定義3:按PV計算CTR,$CTR_{PV}(A)=\frac{A算法下用戶點擊的PV數}{A算法下總的PV數}$
定義4:按UV計算CTR,$CTR_{UV}(A)=\frac{A算法下有點擊的用戶數}{A算法下總的用戶數}$
場景1:按PV划分流量,按PV計算CTR。
這種情況比較簡單,在忽略用戶對算法疲勞度(通常是合理的)的情況下,這種測量對比方案比較合理。
場景2:按PV划分流量,按UV計算CTR。
這個方案可能一些有經驗的同學會覺得不行,另一些同學會覺得問題也不大。事實上,這會導致嚴重的測量誤差,我們用AA測試的效果來分析一下。假定流量分成兩個桶,第1個桶占比是$p_1$,第2個桶占比為$p_2$,且$p_1+p_2=1$。設該算法的PV的轉化率(CTR)為$r$。
這里需要分為兩種情況來討論:
第1種情況:假設產生無論實際的轉化在哪個桶中產生,將轉化率計算到該用戶到達的每個桶中。
對一個訪問次數為$K=k$的用戶,其整體轉化率為$r_k=1-(1-r)^k$,而他出現在第i個桶的概率為$P(b_i \in B|K=k)=1-(1-p_i)^k, i=1,2$,其中$b_i \in B$表示用戶出現在第$i$個桶中。
從而第i個桶按UV計算的CTR為:
$E[R|b_i \in B]=\sum_{k=1}^{\infty}{r_k P(K=k|b_i \in B)}=\sum_{k=1}^{\infty}\frac{r_k P(b_i \in B|K=k)P(K=k)}{P(b_i \in B)}=\frac{\sum_{k=1}^{\infty}{r_k P(b_i \in B|K=k)P(K=k)}}{\sum_{k=1}^{\infty}{P(b_i \in B|K=k)P(K=k)}}$
設$P(K=k)=\alpha_k$,那么:
$E[R|b_i \in B]=\frac{\sum_{k=1}^{\infty}(1-(1-r)^k)(1-(1-p_i)^k)\alpha_k}{\sum_{k=1}^{\infty}(1-(1-p_i)^k)\alpha_k}$
可以證明,$p_i<p_j \implies E[R|b_i \in B]>E[R|b_j \in B]$。
距離來說明這一點,設$p_1=0.1, p_2=0.9$,$\alpha_1=0.5, \alpha_2=0.35, \alpha_3=0.15$,$r=0.015$,即流量比為1:9,訪問次數分別為1,2,3的人比例為10:7:3,按PV算的CTR是0.015。這種情況下,第1個桶按UV算的轉化率為:$E[R|b_1 \in B]=0.0288$,第2個桶按UV算的轉化率為:$E[R|b_2 \in B]=0.0251$。即第1個桶比第2個桶AA測試下按UV統計到的效果好15.11%。也就是說,大桶在該場景下的測試指標比較虧。
不同分桶比例下的AA測試的對比:
小桶流量 小桶CTR 大桶CTR 小桶領先比例 0.0100 0.0292 0.0246 0.1871 0.0200 0.0292 0.0247 0.1831 0.0500 0.0291 0.0248 0.1710 0.1000 0.0288 0.0251 0.1511 0.2000 0.0284 0.0255 0.1117 0.3000 0.0279 0.0260 0.0734 0.4000 0.0275 0.0265 0.0361 0.5000 0.0270 0.0270 0
結論:如果按PV划分流量,按UV計算轉化率,無論交易發生在哪個桶中,將轉化率計算入該用戶到達的每個桶中,大桶在該場景下的測試指標比較虧。直觀的理解是,這種情況下,小桶從大桶的推薦效果中“沾光”要大於大桶從小桶的推薦效果中“沾光”。
第2種情況:轉化發生在哪個桶,就將轉化率算入該桶中。
相對第1種情況,這種情況會更普遍一些,因為它看上去“更公平”,而事實上卻遠非如此。仍然借用第1種情況下的符號,可以得到UV轉化率和PV轉化率的關系如下:
$E[R|b_i \in B]=\frac{\sum_{k=1}^{\infty}{\sum_{l=1}^{k}(1-(1-r)^l){k \choose l}p_i^l(1-p_i)^{k-l}\alpha_k}}{\sum_{k=1}^{\infty}{\sum_{l=1}^{k}{k \choose l}p_i^l(1-p_i)^{k-l}\alpha_k}}$
可以證明,$p_i<p_j \implies E[R|b_i \in B]<E[R|b_j \in B]$。
沿用情況1的各種數據,這種情況下,第1個桶按UV算的轉化率為$E[R|b_1 \in B]=0.0157$,第2個桶按UV算的轉化率為$E[R|b_2 \in B]=0.0234$。即第2個桶比第1個桶AA測試下按UV統計到的效果好48.59%。也就是說,小桶在該場景下的測試指標比較虧,而且相對於第一種情況不公平更加嚴重。
不同分桶比例下的AA測試的對比:
小桶流量 小桶CTR 大桶CTR 大桶領先比例 0.0100 0.0151 0.0244 0.6222 0.0200 0.0151 0.0243 0.6065 0.0500 0.0154 0.0240 0.5603 0.1000 0.0157 0.0234 0.4859 0.2000 0.0165 0.0222 0.3467 0.3000 0.0173 0.0212 0.2199 0.4000 0.0182 0.0201 0.1046 0.5000 0.0192 0.0192 0
結論:如果按PV划分流量,按UV計算轉化率,交易發生在哪個桶中,就將轉化率計算入該桶中,小桶在該場景下的測試指標比較虧。直觀的理解是,這種情況下,小桶中用戶行為次數比大桶中少,因此轉化率低。
場景3:按UV划分流量,按PV計算CTR。
這種情況下每個用戶會被划分到確定的算法處理,如果算法分配到的用戶比較少,而用戶行為差異比較大的情況下,小流量算法的指標會受到一定干擾。但對於大多數情況下也可以合理的忽略這種因素,方案比較合理。
場景4:按UV划分流量,按UV計算CTR。
這種情況下每個用戶被划分到確定的算法處理,參考場景3的結論,方案比較合理。
為什么會造成這樣的問題呢?從本質上講,這是由於AB測試中不同的桶之間的流量會存在交集,這個交集部分的流量無論怎么統計,都可能會產生影響和問題,尤其是統計指標是交集元素的ID(比如用戶ID,cookie等)時,問題更嚴重。只有從根本上杜絕AB測試中的交集,使各個測試桶之間互不影響。
可能有人會對場景2中的流量想到一種這樣的分配方案,來解決兩個測試桶流量不平衡的問題。比如將其中的90%的流量分為兩個部分,一個為80%的流量桶(第3個桶,A算法)不參與測試,一個為10%的流量桶(第2個桶,A算法),再加上另外一個10%的流量桶(第1個桶,B算法)。此時A、B兩個算法的測試桶中的流量大小相等,是不是就公平了呢?
No!原因在於,第2個桶和第1個桶是同一個算法,給用戶展示的結果更接近,因此第1個桶雖然不參與測試,但仍然會形成干擾,這種干擾在不同的效果統計方式下表現為不同的測試偏差。