Estatística

Testes Simultâneos: quando o efeito de interação importa

Por que rodar testes A/B simultâneos costuma ser seguro, como é um efeito de interação de verdade e o bug de atribuição que é bem mais provável que ele.

Ilustração plana de dois retângulos arredondados translúcidos se sobrepondo, com a região comum em tom mais profundo, em tons de verde profundo

Rodar testes A/B simultâneos nos mesmos usuários é o estado normal de um programa de experimentação que funciona, não uma concessão. A premissa que torna isso válido é que cada experimento pode ser analisado isoladamente, o que vale enquanto as atribuições forem independentes e os tratamentos não interagirem, e a forma bem mais comum de essa premissa cair é um defeito de aleatorização, não uma interação genuína. Este guia cobre o que é de fato um efeito de interação, por que a experiência publicada por grandes plataformas é de que eles são raros, os bugs de atribuição que se disfarçam de interação, e um exemplo trabalhado 2x2 que mostra por que “nenhuma interação significativa” normalmente quer dizer que o teste jamais teria conseguido achar uma. Faz parte do nosso guia completo de teste A/B e conversa com testar várias variações.

Sobrepor é o padrão, não a exceção

Em qualquer volume relevante, isolamento deixa de ser acessível. Kohavi e colegas, descrevendo o sistema de experimentação do Bing para o KDD 2013, reportam mais de 200 experimentos simultâneos rodando num dia qualquer, e colocam a combinatória de forma crua: com cinco variantes em cada uma de quinze áreas de experimentação simultâneas, números que eles mesmos chamam de conservadores, os usuários acabam em uma de cinco elevado a quinze, algo perto de 30 bilhões de variantes possíveis do Bing. Ninguém valida 30 bilhões de configurações. O sistema precisa ser construído de forma que validá-las seja desnecessário.

A resposta do Google, descrita por Tang, Agarwal, O’Brien e Meyer para o KDD 2010, é uma infraestrutura em camadas com três conceitos: um domínio é uma segmentação de tráfego, uma camada corresponde a um subconjunto dos parâmetros do sistema, e um experimento é uma segmentação de tráfego em que parâmetros recebem valores alternativos. Parâmetros que não podem variar de forma independente entre si vão para a mesma camada, experimentos dentro de uma camada são mutuamente exclusivos, e o desvio de tráfego para experimentos em camadas diferentes é ortogonal. Uma requisição passa por um experimento por camada.

O exemplo que motiva o desenho deles é o argumento mais curto que existe para a razão de as camadas existirem: com um parâmetro para a cor de fundo da página e outro para a cor do texto, azul é um valor válido para os dois, e se os dois forem azuis ao mesmo tempo a página fica ilegível. Isso é uma interação de verdade, e nenhuma quantidade de estatística conserta. Ela é evitada por construção.

Três formas de agendar experimentos simultâneosCamada única coloca cada usuário em no máximo um experimento, o que é simples mas desperdiça tráfego. Sobreposição total coloca todo usuário em todo experimento com aleatorização independente, o que é eficiente mas assume ausência de interação. Atribuição em camadas agrupa numa mesma camada os parâmetros que não podem variar de forma independente, tornando os experimentos exclusivos dentro de uma camada e independentes entre camadas.Os mesmos quatro experimentos, agendados de três formascamada única: um experimento por usuárioexperimento 1experimento 2experimento 3experimento 4seguro e simples, mas cada experimento fica com um quarto do tráfego e a fila nunca andasobreposição total: todo usuário em todo experimento, hasheado de forma independenteexperimento 1, todo o tráfegoexperimento 2, todo o tráfegoexperimento 3, todo o tráfegopoder cheio para cada um, válido só enquanto as atribuições forem independentes e os tratamentos não interagiremem camadas: exclusivo dentro da camada, independente entre camadascamada A: exp 1 ou exp 2camada B: exp 3 ou exp 4
O esquema em camadas é o ponto em que as plataformas de produção convergem, porque compra a vazão da sobreposição total e ao mesmo tempo torna impossível produzir as combinações que realmente se quebram entre si.

O que é, de fato, um efeito de interação

Kohavi e colegas definem com precisão: existe interação estatística entre dois tratamentos A e B se o efeito combinado dos dois não é igual à soma dos dois efeitos individuais. E logo em seguida nomeiam por que isso importa, numa frase que é a razão inteira de este tópico existir: a existência de interação viola a premissa básica usada para escalar experimentação, a de que cada experimento pode ser analisado isoladamente.

Eles listam três danos. Interações podem prejudicar usuários, porque combinações específicas disparam bugs inesperados. Distorcem resultados de todos os experimentos envolvidos, o que pesa mais quando o efeito real do tratamento é pequeno, já que aí uma interação pequena consegue produzir resultados completamente enganosos numa métrica-chave. E não podem ser totalmente evitadas por testes e checagens offline, porque times diferentes não sabem o que os outros times estão subindo.

Esse é o argumento para levar interação a sério. Aqui vai o argumento para não entrar em pânico com ela, do mesmo artigo: na nossa experiência, interações são relativamente raras e mais frequentemente representam bugs do que interações estatísticas verdadeiras. Eles seguem preferindo atribuição ortogonal, equivalente a um fatorial completo, e rodam testes multivariados pequenos só quando existe interação suspeita ou detectada. O levantamento de 2009 do mesmo grupo faz um argumento vizinho: no mundo online, a disponibilidade de usuários e a agilidade do teste contínuo tornam testes univariados simultâneos preferíveis aos desenhos multivariados tradicionais, cujos arranjos fracionários e de Plackett-Burman confundem interações de dois fatores com efeitos principais de qualquer forma.

A leitura operacional é uma ordem de prioridade: quando a célula combinada parece errada, procure um bug antes de procurar uma interação.

A falha bem mais provável que uma interação

Independência de atribuição é uma suposição, e é uma suposição que esquemas de hash quebram em silêncio. Kohavi, Longbotham, Sommerfield e Henne testaram isso diretamente em 2009. A montagem deles hasheia a concatenação de um identificador de usuário com um identificador de experimento e depois particiona a faixa. Rodaram cinco experimentos simulados contra um milhão de ids sequenciais de usuário e aplicaram testes qui-quadrado procurando correlação entre experimentos. Os resultados:

Função de hash Resultado dos testes de correlação
MD5 Não gerou correlação nenhuma entre experimentos
SHA256 Chegou perto, exigindo uma interação de cinco vias para produzir correlação
O algoritmo de hash de string embutido no .NET Falhou até num teste de interação de duas vias

E aí vem a falha que vale memorizar, porque é uma otimização que qualquer engenheiro competente poderia tentar. MD5 é caro, então um sistema tentou usar cache: hasheia o nome do experimento uma vez, hasheia o id do usuário uma vez, guarda os dois e aplica XOR entre eles na hora de atribuir. O artigo reporta a consequência exata. Com dois experimentos a 50/50, se o bit mais significativo dos hashes dos dois nomes de experimento coincidisse, os usuários sempre receberiam a mesma atribuição nos dois experimentos; se não coincidisse, os usuários receberiam exatamente a atribuição oposta. De um jeito ou de outro as atribuições ficam perfeitamente correlacionadas e os resultados dos dois experimentos ficam confundidos.

Nada disso aparece como número estranho em nenhum dos dois experimentos lido isoladamente. Os dois parecem normais. Fabijan e colegas (KDD 2019) listam a mesma propriedade como a terceira exigência de um serviço de atribuição, ao lado de probabilidade igual e consistência entre visitas repetidas: quando vários experimentos rodam, não pode existir correlação entre experimentos. O jeito de achar uma violação é procurar por ela, que é o argumento a favor de um experimento de validação permanentemente no ar, coberto em teste A/A, e das checagens de divisão em SRM, a divisão desigual de tráfego.

Atribuição independente contra atribuição correlacionadaCom hash independente, os usuários se espalham de forma aproximadamente uniforme pelas quatro combinações de dois experimentos simultâneos, dando a cada experimento uma comparação limpa. Com hash correlacionado, os usuários caem só nas duas combinações coincidentes, então as duas células da diagonal ficam vazias e nenhum dos dois experimentos pode ser separado do outro.Onde os usuários caem em dois experimentos 50/50 simultâneoshash independenteexp 2 controleexp 2 variaçãoexp 1 controle25%25%exp 1 variação25%25%cada experimento tem uma comparação completa dentro do outrohash correlacionado (o atalho com XOR)exp 2 controleexp 2 variaçãoexp 1 ctrl50%0%exp 1 var0%50%os dois experimentos confundidos, e os dois lendo normal
A grade da direita é o que o atalho de cache com XOR produz quando os hashes de dois nomes de experimento compartilham o bit inicial. Cada experimento ainda mostra uma divisão plausível, uma taxa de conversão plausível e um valor-p plausível.

Exemplo trabalhado: um fatorial 2x2, e por que a interação não diz nada

Dois times sobem ao mesmo tempo no mesmo fluxo de checkout. O experimento A muda o aviso de custo de frete. O experimento B muda o botão de pagamento. A atribuição é independente, então os usuários caem em quatro células de 50.000 cada, a uma taxa base de conversão de 4 por cento. Cole as células na calculadora conforme for lendo:

Calculadora de significância estatística
Controle (A)
Variação (B)
Controle (A) · Taxa-
Variação (B) · Taxa-
Melhora relativa-
valor-p-
IC 95% da diferença-

Teste z bilateral de duas proporções. "Sem significância" quase sempre quer dizer que falta amostra, não que as versões são iguais.

Célula Usuários Conversões Taxa
Nenhuma das mudanças 50.000 2.000 4,000 por cento
Só A 50.000 2.120 4,240 por cento
Só B 50.000 2.090 4,180 por cento
A e B juntos 50.000 2.215 4,430 por cento

Efeito principal de A. Colapsando sobre B: 4.090 conversões em 100.000 sem A contra 4.335 em 100.000 com A. Isso é 4,090 por cento contra 4,335 por cento, mais 0,245 ponto percentual, mais 5,99 por cento relativo, z = 2,73, valor-p 0,0064, intervalo de mais 0,069 a mais 0,421 ponto percentual.

Efeito principal de B. Colapsando sobre A: 4.120 contra 4.305 em 100.000 cada, ou seja 4,120 por cento contra 4,305 por cento, mais 0,185 ponto percentual, mais 4,49 por cento relativo, z = 2,06, valor-p 0,0395, intervalo de mais 0,009 a mais 0,361 ponto percentual.

A interação. O efeito de A quando B está desligado é 4,240 menos 4,000, ou seja mais 0,240 ponto percentual. O efeito de A quando B está ligado é 4,430 menos 4,180, ou seja mais 0,250 ponto percentual. A interação é a diferença dessas diferenças: mais 0,010 ponto percentual. O erro padrão dela é a raiz quadrada da soma das quatro variâncias de célula, o que dá 0,1797 ponto percentual, resultando em z = 0,06, valor-p 0,9556, intervalo de menos 0,342 a mais 0,362 ponto percentual.

Lido ao pé da letra, isso diz que não há interação. Lido com honestidade, diz algo mais fraco e muito mais útil. O erro padrão da interação é exatamente o dobro do erro padrão de um efeito principal, que é o resultado geral para uma diferença de diferenças e a razão de uma interação de um dado tamanho exigir cerca de quatro vezes a amostra de um efeito principal daquele tamanho. Neste desenho, a menor interação detectável a 80 por cento de poder é 0,491 ponto percentual, algo perto de 12,3 por cento relativo, enquanto os efeitos principais se resolvem até cerca de 0,246 ponto percentual.

Então a frase correta no relatório não é “não há interação entre A e B”. É “nenhuma interação maior que cerca de meio ponto percentual era detectável nesta amostra, e a distância observada é de 0,01”. Como cada efeito principal é menor que a interação que o teste conseguiria enxergar, uma interação grande o bastante para mudar qualquer uma das duas decisões teria aparecido. Esse é o argumento que de fato autoriza subir os dois, e é um argumento de poder, não de valor-p. A mesma disciplina de leitura vale para qualquer resultado inconclusivo, como cobrimos em efeito mínimo detectável.

Efeito combinado observado contra a previsão aditivaSem nenhuma das mudanças a taxa é 4,000 por cento. Só A dá 4,240 por cento e só B dá 4,180 por cento. Somar os dois efeitos individuais prevê 4,420 por cento para a célula combinada, e a célula combinada observada é 4,430 por cento, uma distância de 0,010 ponto percentual contra um limiar detectável de cerca de 0,491.A célula combinada cai onde a aditividade previu, dentro de uma margem larga3,94,14,34,54,000nenhuma4,240só A4,180só B4,430os doisprevisão aditiva 4,420Distância de 0,010 ponto contra um limiar detectável de 0,491 ponto. O desenho não conseguiria resolver uma interação pequena, só uma grande.
A altura das barras é a taxa de conversão em por cento. A linha tracejada é o que a célula combinada deveria ser se as duas mudanças simplesmente somassem, e a barra observada cai em cima dela, dentro de um intervalo muito mais largo que a distância.

Testar todos os pares não escala, e o Bing diz isso

Se você decidir checar interação em todos os pares de experimentos em curso, a contagem de pares cresce de forma quadrática e os falsos positivos crescem junto:

Experimentos simultâneos Pares a testar Chance de ao menos um par parecer interativo por acaso, a 5 por cento
2 1 5,0 por cento
4 6 26,5 por cento
6 15 53,7 por cento
10 45 90,1 por cento
15 105 99,5 por cento
20 190 99,99 por cento

Kohavi e colegas colocam o problema exatamente nesses termos: se estamos rodando N experimentos por vez, a complexidade de detectar interações par a par é quadrática em N, e por causa da escala o sistema deles precisa às vezes rodar centenas de milhares de testes de hipótese. A resposta deles não é parar de testar, e sim controlar a taxa de erro, usando um algoritmo bayesiano empírico de taxa de descoberta falsa para identificar os casos com maior chance de serem verdadeiros positivos, depois do que a ferramenta roda um diagnóstico mais fundo e alerta os donos do experimento.

Para um time que roda um punhado de experimentos em vez de centenas, a versão prática é mais simples: não varra interações par a par por padrão. Cheque um par específico quando houver motivo, e se for checar muitos, aplique correção, a mesma aritmética coberta em testar várias variações.

Decidindo o que isolar

Situação Sobrepor ou isolar Por quê
Duas mudanças em superfícies sem relação, por exemplo checkout e onboarding Sobrepor A premissa de independência é plausível e o tráfego vale mais em outro lugar
Duas mudanças no mesmo elemento ou no mesmo parâmetro de configuração Isolar É o caso da cor de fundo com a cor do texto; a combinação pode ser quebrada por construção
Duas mudanças na mesma página, em elementos diferentes Sobrepor, mas declarar o par como um a checar depois Interações são raras, mas é aqui que elas se concentram
Uma mudança que altera quem é elegível para o outro experimento Isolar Elegibilidade vira variável pós-tratamento e as duas leituras ficam comprometidas
Quaisquer dois experimentos cujo estado combinado nunca foi construído nem revisado Isolar até revisar A interação real mais comum é um bug numa combinação não testada
Uma mudança de preço ou de cobrança junto com qualquer coisa Isolar Estados combinados aqui são caros de errar e difíceis de reverter

Prevenção ganha de detecção, e os mecanismos usados em escala valem ser copiados em escala pequena. O Bing, segundo o artigo de 2013, faz cada experimento declarar um conjunto de restrições para que o sistema se recuse a rodar experimentos conflitantes juntos, por exemplo garantindo que um usuário nunca esteja em dois experimentos de visual de anúncio ao mesmo tempo; usa gestão de configuração para detectar experimentos tentando mudar o mesmo parâmetro antes do lançamento; e, quando interações não podem ser evitadas, usa mapeamentos para excluir usuários de um experimento do outro. As camadas de lançamento e os domínios aninhados do Google, segundo o artigo de 2010, são a mesma ideia expressa como infraestrutura.

Erros comuns com testes simultâneos

Erro O que produz
Reusar um único hash do id do usuário em todos os experimentos Todo experimento recebe a mesma divisão de usuários, e todos ficam confundidos
Guardar hashes em cache e combiná-los com XOR Atribuição perfeitamente correlacionada ou perfeitamente oposta, conforme o levantamento de 2009
Ler “nenhuma interação significativa” como “nenhuma interação” Uma conclusão que o desenho tinha algo perto de uma moeda de chance de sustentar
Varrer todos os pares em busca de interação sem controle de multiplicidade Com dez experimentos, cerca de 90 por cento de chance de ter uma interação falsa para perseguir
Serializar todo experimento para evitar interação O risco mais raro evitado ao custo da vazão do programa inteiro
Rodar dois experimentos no mesmo elemento e ler os dois como limpos A única configuração em que interações de fato se concentram
Tratar uma interação suspeita como estatística antes de checar se é bug Contradiz a experiência publicada de que interações mais frequentemente representam bugs
Deixar um experimento mudar a elegibilidade para outro Seleção pós-tratamento, de que nenhuma análise se recupera

Faça isso automático na Donnu

Testes simultâneos são seguros quando a plataforma torna as atribuições independentes e avisa quando elas deixam de ser. A Donnu A/B tempera o hash de atribuição com o identificador do experimento, então dois experimentos nunca herdam a divisão um do outro, roda a checagem de proporção de amostra em todo experimento e não só naquele que você está olhando, e permite declarar um experimento mutuamente exclusivo com outro quando a combinação não deveria existir. A sobreposição segue sendo o padrão, porque é o que permite um time pequeno rodar mais de um teste por vez, e o isolamento fica disponível para os pares específicos que precisam dele.

Comece um teste grátis de 14 dias e rode seus próximos dois experimentos ao mesmo tempo sem ficar adivinhando se eles colidem.

Referências

Leia também: Teste A/A · Testar várias variações · SRM: divisão desigual de tráfego · Efeito mínimo detectável · Calculadora de significância A/B/n grátis · Read in English

Perguntas frequentes

Posso rodar vários testes A/B ao mesmo tempo nos mesmos usuários?
Pode, e em qualquer escala real você não tem escolha. Kohavi e colegas (KDD 2013) descrevem mais de 200 experimentos simultâneos rodando no Bing num dia qualquer, com usuários caindo em uma de cerca de 30 bilhões de variantes possíveis do site. A exigência não é isolamento, é aleatorização independente: a atribuição de um usuário em um experimento não pode alterar a probabilidade da atribuição dele em outro. Com isso em pé, cada experimento pode ser analisado sozinho.
O que é um efeito de interação entre dois experimentos?
Existe interação estatística entre os tratamentos A e B quando o efeito combinado dos dois não é igual à soma dos dois efeitos individuais, como Kohavi e colegas (KDD 2013) definem. Na versão simples: se A dá mais 0,24 ponto sozinho e B dá mais 0,18 sozinho, a aditividade prevê mais 0,42 quando os dois rodam juntos. A interação é a distância entre essa previsão e o que a célula combinada de fato mostra. O problema é que essa distância viola a premissa que permite analisar cada experimento isoladamente.
Efeito de interação é comum na prática?
É raro. Kohavi e colegas (KDD 2013), escrevendo de uma plataforma que roda centenas de experimentos por dia, afirmam que na experiência deles as interações são relativamente raras e mais frequentemente representam bugs do que interações estatísticas verdadeiras. É por isso que eles continuam preferindo atribuição ortogonal, equivalente a um fatorial completo, a teste multivariado. A consequência prática é direta: uma interação suspeita deve ser investigada primeiro como defeito e só depois como estatística.
De quanta amostra eu preciso para detectar uma interação?
Cerca de quatro vezes o que você precisa para um efeito principal do mesmo tamanho, porque a interação é uma diferença de diferenças e o erro padrão dela é aproximadamente o dobro. Num desenho 2x2 com 50.000 usuários por célula a uma taxa base de 4 por cento, um efeito principal se resolve até cerca de 0,25 ponto percentual a 80 por cento de poder, enquanto a interação só se resolve até cerca de 0,50. Ou seja, a maioria dos testes que reporta nenhuma interação significativa nunca teve poder para achar uma, e a frase honesta é que nenhuma interação maior que X foi detectada.
O que quebra de verdade quando experimentos se sobrepõem?
Correlação de atribuição, bem mais frequentemente que uma interação genuína. Kohavi e colegas (2009) testaram cinco experimentos simulados contra um milhão de ids sequenciais de usuário e acharam que só o MD5 não produziu correlação entre experimentos, enquanto o hash de string embutido no .NET falhou até num teste de duas vias. Eles também documentam um atalho de cache que aplicava XOR entre o hash do experimento e o hash do usuário, o que fazia os usuários caírem em atribuições idênticas ou exatamente opostas nos dois experimentos dependendo de um único bit. Os dois experimentos ficam confundidos e nenhum dos dois é legível.
Quando dois experimentos devem ser mutuamente exclusivos?
Quando a combinação pode produzir uma experiência quebrada ou nociva, quando duas mudanças tocam a mesma superfície ou o mesmo parâmetro de configuração, ou quando existe suspeita concreta de interação. Tang e colegas (KDD 2010) dão a ilustração mais limpa: com um parâmetro para a cor de fundo da página e outro para a cor do texto, azul é um valor válido para cada um e um desastre para os dois ao mesmo tempo. A resposta deles é agrupar numa mesma camada os parâmetros que não podem variar de forma independente, de modo que experimentos dentro de uma camada sejam exclusivos e camadas diferentes se sobreponham livremente.
Devo testar interação entre todos os pares de experimentos rodando?
Só com controle de multiplicidade, porque a contagem de pares cresce de forma quadrática. Dez experimentos simultâneos formam 45 pares, o que a um limiar de 5 por cento dá cerca de 90 por cento de chance de ao menos um par parecer interativo só por acaso. Kohavi e colegas (KDD 2013) descrevem monitorar todos os experimentos em curso em busca de interações par a par, às vezes rodando centenas de milhares de testes de hipótese, e usar um algoritmo bayesiano empírico de taxa de descoberta falsa para segurar os falsos positivos.