Recomendação de Textos sem dor de cabeça: Teoria e Prática com ElasticSearch

Allan Sene
Tableless
Published in
6 min readMar 30, 2017

--

Um dos conceitos que consegue ser mais simples e ao mesmo tempo muito complexo em Recuperação de Informação é a Recomendação de Textos com base em Conteúdo. Sistemas de Recomendação estão para todo lado hoje em dia, desde da lista de séries que o Netflix lhe recomenda até as notícias ruins que o Facebook insiste em lhe mostrar. Mas o que às vezes parece ser tão difícil de entender e, mais ainda, de implementar não está tão longe das nossas mãos, desenvolvedores pragmáticos que precisamos mais da solução que do problema.

Coisa que pouca gente sabe sobre o ElasticSearch, banco NoSQL que ganhou imenso espaço no mercado nos últimos anos, principalmente para guardar logs e outros dados semi-estruturados, é que, além de ser muito fácil de clusterizar, monitorar e integrar, é uma ferramenta absurdamente parruda para Busca por Similaridade de Conteúdo.

Mas o que é isso?

Imagine que você tem um artigo no seu blog sobre Futebol. Nesse artigo especificamente, você discorre sobre aqueles jogadores que falsificam documentos para parecerem mais jovens: o famoso “Gato”.

Sem colocar tag ou categoria alguma, o Medium recomenda pra quem leu seu texto, os artigos do Juca Kfouri. Mas como isso foi possível, se você não disse nada?

Mais um caso de gato no futebol

O que aconteceu foi uma Recomendação com base no Conteúdo do seu texto. Ninguém precisou dizer para o Medium, por meio de tags ou qualquer classificação, que você não estava falando sobre gatinhos invadindo um campo ou sobre jogadores galãs. O sistema de recomendação do Medium analisou seu texto e percebeu que ele se aproxima mais do Futebol do que de gatinhos fofos.

Uma pitada de Teoria

Para entender a mágica da moeda que os computadores fazem para recomendar textos necessitamos basicamente de 2 conceitos.

Se quiser, pode pular pra parte da Intuição logo abaixo que vai ser o suficiente para entender tudo. Se for ler tudo, recomendo que saia catando os links de referência.

TF/IDF

Caracterizar um texto entre outros diversos num conjunto, comumente chamado de Corpus, é uma tarefa relativamente simples. A estrutura de dados mais comum para representá-lo é a Bag of Words: nada mais é que um array de palavras, sem repetição, cada uma em sua posição. Dessa forma, podemos resumir um texto em um array de tuplas {palavra, quantidade_que_esta_aparece_no_texto}.

Já TF/IDF é um acrônimo para Term Frequency/Inverted Document Frequency:

  • TF: Frequência de Termos - Quantas vezes cada palavra em cada texto.
  • IDF: Inverso da Frequência nos Documentos - inverso de quantas vezes cada palavra aparece nos outros textos do corpus.

Vamos visualizar pra ficar mais claro:

Uma representação concisa e barata (memória) de um Corpus.

Percebe que temos estes 2 valores nessa matriz? TF de cada documento está nas colunas e o IDF é o inverso da soma das linhas de cada termo.

Modelo Vetorial

Podemos concluir que temos um modelo vetorial para representação de um texto, digamos que temos o conteúdo. Mas e agora? Como calcular a similaridade?

Lembrando das aulas de GAAL: a forma mais comum de quantificar a distância entre 2 vetores no espaço, independentemente de quantas dimensões este tem, é com o Produto Vetorial. Abaixo temos uma representação de 3 sentenças nesse espaço vetorial. No eixo X, temos a quantidade de Termos 1 na sentença, no Eixo Y, do Termo 2 e assim por diante…

A representação dos termos no Corpus é análoga a da gravura acima, trocando apenas sentença(vetores) por termos e os termos (eixos) por documentos.

Intuição desse negócio…

Moisés também não consegue entender bem esse trem de vetores, espaço, raquete…

É meio complicado esse negócio? Não faz mal… Voltemos ao exemplo do seu artigo sobre Gato no Futebol. Seu artigo tem um monte de palavras relacionadas a futebol: técnico, time, Flamengo, Copa São Paulo e por aí vai… Esses termos são frequentes em todos os outros textos também, logo um indício de proximidade/semelhança entre eles.

Mas como que ele ainda consegue ser identificado como um texto que fala sobre aqueles caras que falsificam documentos para passarem nas peneiras e não sobre os bonitões do time da Itália ou sobre gatinhos invadindo o Morumbi?

Tá aí o segredo do tal IDF — nos outros textos sobre Futebol, as palavras “falsificação”, “golpe” e “GATO” raramente estão juntas. Então, se elas estão juntas, OBVIAMENTE representam um conceito único e que é relevante no contexto do futebol.

Desenhou a raquete! Aê!! Agora que ficou tudo mais claro, vamos pra prática!

Tudo isso ao seu alcance!

Implementar isso tudo deve ser um pé no saco, né?! Por sorte nossa, o ElasticSearch, cara que citei lá no começo, tem tudo isso built-in, pronto pra uso, só indexar os documentos lá e fazer as consultas!

Mais disso aqui, por favor…

Uma das coisas mais legais do ElasticSearch é que tudo nele pode ser feito a partir de uma interface REST. Nesse caso para Busca com base em Conteúdo, tem a Query do tipo More Like This na própria API Search.

Suponha que você tenha indexado lá dentro do ES, vários posts e você quer buscar aqueles textos que tenham o corpo ou o título que mais se parecem com o seu artigo “Sobre gatos no futebol”. Você faz uma simples consulta assim:

GET /_search
{
"query": {
"more_like_this" : {
"fields" : ["título", "corpo_do_texto"],
"like" : [
{
"_index" : "medium",
"_type" : "artigos",
"_id" : "sobre_gatos_no_futebol-1.0.1"
}
}
}
}

Como mágica, o ES vai retornar os textos que mais são similares com o seu, em ordem. E numa velocidade incrível, pois esses caras já foram todos calculados antes! Você pode também mandar um trecho direto pra query que ele calcula o TF/IDF do seu texto na hora e traz os resultados do mesmo jeito. Muito bacana né :) Tudo isso vem lá do Lucene, core do motor de busca do ES, mas que não vamos entrar em detalhes aqui nesse post.

Pra quem tiver maior interesse, pode dar uma olhada num projetinho avacalhado que eu fiz numa hackathon há algum tempo: o Ask ’n’ Go, recomendador de respostas para fóruns de disciplinas. O código não tá aqueeelas coisas, mas dá pra ver a gente usando a API do ES pra buscar as respostas mais relevantes dado uma pergunta, além de como indexar documentos e tals.

Pois bem, pessoal… Nesse artigo deu pra ter uma idéia de que por mais distante que possam parecer certos conceitos no nosso meio, sempre tem algum pontinho por onde começar a estudar. Essa área de Sistemas de Recomendação é gigantesca, contudo muito instigante, além de ter muito espaço a crescer ainda no mercado de software.

Espero que tenham gostado deste artigo mais teórico/técnico. Se não gostaram ou acharam alguma baboseira no que eu escrevi, não deixe de comentar.

Abraço e até a próxima!

--

--

Allan Sene
Tableless

CTO | Lead Data Engineer | Co-Founder of Data Hackers and Dadosfera. Loves science, code and cats ^*^