segunda-feira, 6 de abril de 2015

Seleção de variáveis usando Random Forest.

No post de hoje iremos discutir um tema muito importante e que vem ganhando cada vez importância neste mundo de big data: a seleção de variáveis.
A cada dia temos mais e mais informações de tudo o que acontece em nossa volta, o que significa que nossos problemas de predição têm a cada dia novas variáveis explicativas disponíveis. É claro que quanto mais dados melhor, no entanto, isto acaba dificultando, do ponto de vista computacional e estatístico, para a escolha do melhor subconjunto de variáveis nesta imensidão de dados. Atualmente, em média, os problemas nos quais trabalho apresentam cerca de 1.000 a 3.000 features, mas já participei de projetos com mais de 40.000 variáveis.
O que acontece é que dentre estas 40.000 variáveis, há muitas que são consideradas não informativas, ou seja, que não têm relação nenhuma com aquilo que queremos prever. Outro ponto é que há muitas variáveis que contêm as mesmas informações. Estes fatores, se não tratados, podem causar o que chamamos de overfitting que é a construção de uma solução que pode ser muito boa apenas para seus dados mas não consegue generalizar para novas amostras. Além disso, com este número de variáveis dificilmente conseguiremos interpretar algum resultado.
Para contornar estes problemas existe a etapa de seleção de variáveis, que faz parte de quase todos os projetos de aprendizado. Basicamente, a etapa de seleção de variáveis consiste em tentar escolher o subconjunto de variáveis que forneça a melhor predição possível.
Muitas das técnicas de machine learning não foram feitas para lidar com esta quantidade de variáveis, no entanto, é importante ressaltar que algumas técnicas de aprendizado já realizam uma seleção de variáveis, como o LASSO (Least Absolute Shrinkage and Selection Operator), que podemos discutir com mais detalhes em um futuro post. Muitos de vocês devem estar pensando, por que não construímos todas as combinações possíveis e escolhemos o melhor subconjunto de variáveis. A resposta é porque não temos hoje poder computacional suficiente. Por exemplo, se tivéssemos 10 variáveis disponíveis, o número total de combinação de subconjuntos para estimarmos seria 2^10 que são 1024 modelos, o que representa um número plausível. Mas imagine agora que temos 1.000 variáveis, o que não é difícil atualmente. Neste caso o número total de ajustes necessários é 2^1000 que é um número muito, mas muito maior que o número estimado de estrelas no universo.
A técnica de random forest tem como objetivo fornecer previsões de algum fenômeno e surgiu a partir dos métodos de bagging. O método de bagging (bootstrap aggregation) consiste em “n” repetições de uma mesma técnica de aprendizado em várias amostras de bootstrap, sendo mais comum o uso de árvores de decisão. Assim, a estimativa final de cada observação será a média destas “n” árvores no caso de variável resposta contínua e na maioria de votos no caso de problemas de classificação. Esta técnica tem mostrado maior performance em relação ao uso de uma única árvore basicamente por diminuir a variância, pois


Podemos perceber pela fórmula acima que quanto menor for a covariância entre as diferentes estimativas maior deverá ser a performance esperada. Assim, surgiu a ideia do random forest, que tenta diminuir exatamente esta covariância entre as estimativas. Para atingir tal objetivo, além de a cada iteração a amostra de bootstrap ser alterada, as variáveis disponíveis para serem utilizadas na árvore também são alteradas.
Além de frequentemente superar um único classificador, o random forest, assim como o bagging, apresenta a grande vantagem de serem compostas por várias árvores independentes. Assim, o paralelismo e até mesmo a programação em map reduce podem ser alcançadas facilmente.
O objetivo deste post não é explicar com detalhes a técnica de random forest. Caso seja do interesse do leitor, maiores informações podem ser encontradas no livro “The Elements of Statistical Learning” de Hastie, Tibsharani e Friedman.
Além de obter bons resultados em termos de predição, o método de random forest também tem alcançado resultados satisfatórios quando o objetivo é seleção de variáveis, superando vários métodos conhecidos e historicamente utilizados. O algoritmo de importância das variáveis consiste em cada iteração:

  • Amostra de bootstrap da base. Cerca de 37% da amostra original não é escolhida na amostra de bootstrap e consiste na amostra out-of-bag desta iteração;
  • Aleatorização das variáveis para serem utilizadas na árvore;
  • Construção da árvore de decisão;
  • Aleatoriamente, para cada variável separadamente, permute seus valores e verifique quanto alguma medida de performance, como por exemplo o Gini Index, é alterado na amostra out-of-bag em relação a performance sem a perturbação.
Repita este processo para todas as árvores construídas. A importância de cada variável será a média do delta de performance em todas as árvores. Assim, a variável mais importante será aquela que, quando perturbada, mais altera o desempenho do nosso classificador.
                O resultado final será o ranking de variáveis em que poderemos trabalhar com as melhores variáveis e construir nosso modelo final, por exemplo, uma regressão logística, utilizando apenas as melhores variáveis explicativas e assim evitando diversos problemas citados anteriormente.
                No entanto, nem tudo são flores. Alguns estudos recentes mostram alguns vieses com esta técnica de seleção. Um bastante conhecido é quando temos muitas variáveis à disposição, mais de 200. Nestes casos, precisaremos de muitas árvores para gerar um resultado satisfatório e, além disso, se tivermos muitas variáveis fracas, teremos muitas árvores construídas apenas com estas variáveis, o que prejudicará a seleção final. Para contornar este problema, podemos utilizar antes alguns métodos de seleção por filtro para eliminarmos as piores variáveis antes de utilizarmos o random forest e obtermos o ranking final. Falaremos sobre algumas opções em um post futuro.
                Para exemplificar o uso do algoritmo de random forest para seleção de variáveis com o software R, disponibilizo no GitHub (https://github.com/carlosrelvas/RandomForest_varselection) um código utilizando a library randomForest. Os dados são provenientes de um exemplo de classificação em que o objetivo é classificar um e-mail como um spam ou não spam. Estes dados estão disponíveis no GitHub, mas também estão na seguinte fonte (http://archive.ics.uci.edu/ml/datasets/Spambase) e contém 57 variáveis explicativas.
                Com estes dados, construímos 500 árvores para fazer a seleção, obtendo o seguinte gráfico que apresenta no eixo x cada uma das variáveis explicativas e no eixo y a medida de performance obtida. Colocamos o gráfico em ordem decrescente para melhorar a visualização. Podemos notar que as primeiras 15/16 variáveis se destacam em relação às demais. Por conta disso, utilizamos estas variáveis em um modelo logístico obtendo um Gini de 93,4 e 92,2, nas bases de treino e de teste respectivamente.
                Como esta base é pequena, construímos as 500 variáveis em cerca de 35 segundos. Este número pode ser diminuído consideravelmente com a versão do random forest em map reduce.