Você está na página 1de 3

18/06/13

Lucene - uma aproximao simples a este poderoso motor de busca [Wiki Portugal-a-Programar]

Wiki Portugal-a-Programar
revistaprogramar_arquivo: 15_edicao: Lucene

Lucene - uma aproximao simples a este poderoso motor de busca


ndice
1. 2. 3. 4. O que o Lucene Onde usado o Lucene Como funciona ou Lucene Exemplos de cdigo com PyLucene

1. O que o Lucene
O Lucene talvez dever-se-ia tratar por a Lucene, uma vez que se trata de uma biblioteca de recuperao de informao textual (do ingls information retrieval) de cdigo aberto e criada por Doug Cutting. Originalmente, foi escrita em Java, mas foi rapidamente adaptada a outras linguagens de programao, nomeadamente Python (Pylucene), Perl (Plucene), C# (Lucene.net), C++ (CLucene), e Ruby (Ferret). Contudo, estas adaptaes esto normalmente ligeiramente atrasadas no que toca verso original em Java, actualmente mantida e alojada pela Apache Sofware Foundation. Simples de aprender a usar, mas poderosa nas mos de um programador experiente, esta biblioteca suporta desde ndices estticos com um campo, at mltiplos ndices em paralelo, com centenas de campos e milhares de acessos simultneos. ideal para todo o tipo de projectos, desde o simples website com a search box at um grande motor de busca sobre, por exemplo, a coleco de PDFs que se tem no disco rgido.

2. Onde usado o Lucene


Provavelmente desconhecido para o leitor, o certo que j passou os dedos por esta til ferramenta. Ao fim de contas, quem nunca pesquisou no site Sourceforge, ou na CNET, ou mesmo at na Wikipedia? Para os utilizadores de Ubuntu, quem nunca tirou partido do software de indexao recentemente incorporado na distribuio: o Beagle. Este, no mais que suportado pela Lucene.Net, a implementao em C# desta biblioteca. Assim, a utilizao desta biblioteca por estas entidades (re)afirma por si s a qualidade e a utilidade da mesma.

Trs. Como funciona ou Lucene


O modo de funcionamento do Lucene trivial de se perceber, mas mais complexo de se manusear na perfeio. Para comear, como j se indicou, h uma palavra chave em todo o processo: ndice. O ndice no passa de uma estrutura altamente ordenada de texto, ou de pedaos de texto (tokens), que torna a pesquisa muito mais eficiente. Porm, falha na capacidade de compresso de dados. Um ndice de 6 milhes de abstracts cientficos atinge facilmente os 1.7 GB, no caso de armazenar apenas tokens, ou os 6.6 GB caso guarde o texto. Esta diferena de tamanho vai, obviamente, afectar a performance. Da, uma vantagem para a pesquisa, ter o ndice fragmentado em vrios sub-ndices, de modo a cada um ter menos volume de informao. O modo como o texto tratado pelo Lucene, tambm alvo de ateno. Ao lermos texto para o lucene, ele ser primeiro submetido a um processo chamado analisador (analyzer), que pode ter vrias formas: Standard, Simple, Stop, regional, etc. Sem entrar em grandes explicaes, cada analisador trata o texto de maneira diferente. Uns ignoram a pontuao, outros so especficos para certas lnguas (como a nossa com o ~ e os acentos), outros ignoram palavras comuns, baseando-se numa lista de stopwords, etc. De seguida, tem que se criar um ndice, que pode ser, na maior parte das vezes, ou baseado no disco rgido (acesso mais lento), ou na memria RAM (temporrio). Uma estratgia para aumentar a velocidade de construo do ndice passa por criar o ndice na RAM e no fim, despej-lo para o disco rgido. Na pesquisa, o mesmo ndice pode voltar a ser lido para a RAM, potenciando (muito significativamente) a performance. Tendo o ndice criado, h que criar um escritor de ndices, de modo a popul-lo com os nossos textos. Das vrias opes a passar ao escritor, esto o analisador em causa e o ndice previamente criado. A insero de documentos no ndice faz-se por ltimo, adicionando documento a documento, criando os campos que forem precisos (por exemplo, a data de criao de um ficheiro, e o seu contedo, ou o ttulo de um livro, a sua editora, autor, ano de lanamento, e preo). Quantos mais campos, mais lento ficar o ndice, mas mais especfica poder ser a nossa pesquisa. Tomando o exemplo da livraria, podemos pesquisar apenas por editora, ou por ano de lanamento, ou mesmo por preo. A maneira de guardar a informao tambm varia. Podemos ter a necessidade de guardar alguns campos para mais tarde devolver ao utilizador que pesquise, mas outros campos podem ser fteis e so apenas guardados tokens dos mesmos. Estes tokens so fragmentos nicos do texto e no esto disponveis para futuras recuperaes. Exemplificando, um resumo de um artigo cientfico est dividido em ttulo e resumo. Podemos pesquisar sobre os resumos por uma determinada palavra, sendo devolvidos os ttulos que correpondem nossa pesquisa. No fim do ndice criado, pode-se, opcionalmente, mas sempre recomendado, passar por um processo de optimizao que vai aumentar a performance da pesquisa no ndice recem criado. Este processo vai reduzir os segmentos do ndice a apenas um, facilitando assim a tarefa de abrir o ndice, em vez de mltiplos pequenos ficheiros. Explicaes sobre a formao destes segmentos esto para alm do mbito deste artigo, bastando apenas dizer que so resultado da construo do ndice, podendo ser imaginados como sub-ndices que degradam a performance devido ao seu diminuto tamanho e contedo. Aps se ter um ndice, resta programar o pesquisador. O pesquisador vai usar um pesquisador de ndices (IndexSearcher), que vai precisar da directoria do ndice (tal como o IndexWriter), e de um parser da pesquisa (QueryParser), que vai depender do nome do campo onde pesquisar e de um analisador (igual ao usado na construo do ndice). Recuperam-se depois os resultados, que esto num iterador, e depois vai-se retirar de cada objecto-resultado o campo pretendido (voltando ao exemplo do artigo cientfico, o ttulo do artigo). Os resultados esto ordenados por ordem de relevncia. O prprio Lucene tem um mecanismo de atribuio de relevncia, baseado no TF-IDF, que d mais peso a documentos com maior frequncia do termo, e a termos pouco comuns no geral. Desta forma, simples construir UM motor de pesquisa, desde que tenho maneira de ler os arquivos (parser de PDFs para PDFs por exemplo). A documentao oficial do projecto bastante completa e simples de seguir, fornecendo UM Caminho perfeito para tirar as dvidas que possam surgir. Para alem disse, H muitas mailing-lists que ajudamo os novatos. A cereja no topo do bolo, a incluso de vrios scripts exemplo na Distribuio do Lucene, e PyLucene por exemplo. Estes exemplos So UM timo ponto de partida para o Lucene.

4. PyLucene: usando o Lucene em Python


wiki.portugal-a-programar.pt/revistaprogramar_arquivo:15_edicao:lucene#conclusao 1/3

18/06/13

Lucene - uma aproximao simples a este poderoso motor de busca [Wiki Portugal-a-Programar]

A biblioteca PyLucene est disponvel desde, pelo menos, 2004. Criada e mantida por uma nica pessoa, Andi Vadja, veio no s trazer aos utilizadores de Python o poder do Lucene, como tambm o fez de uma forma extremamente simplista e fiel biblioteca original. De incio, havia duas implementaes: GCJ e JCC. Porm, desde a verso 2.3.0 do Lucene, a implementao em GCJ foi deixada de parte. As principais diferenas entre as implementaes traduziam-se na velocidade de pesquisa, onde a GCJ liderava por larga margem, velocidade de indexao, onde era a JCC a levar a melhor, e noutras caractersticas como o tamanho dos ndices suportados (maior na JCC) e maior estabilidade (JCC). Contudo, o processo de instalao tornou-se mais complicado, da que apesar das fontes serem cedidas para compilao pelo utilizador, h quem disponibilize verses binrias para os mais novatos.

5. Exemplos de cdigo
Tal como qualquer biblioteca em Python, chama-se o Lucene da seguinte forma:
i m p o r t a oL u c e n e

Porm, isto no chega. Com a implementao JCC, trabalha-se dentro de uma mquina virtual de Java, sendo portanto necessrio cri-la, podendo definir-se os seus parmetros (maxheap - limite mximo de memoria RAM a ser usado, initialheap - memria RAM a ser usada inicialmente, etc):
l u c e n e . i n i t V M ( l u c e n e . C L A S S P A T H ) l u c e n e . i n i t V M ( l u c e n e . C L A S S P A T H ,m a x h e a p = 8 0 0 m ) l u c e n e . i n i t V M ( l u c e n e . C L A S S P A T H ,m a x h e a p = 2 g ) l u c e n e . i n i t V M ( l u c e n e . C L A S S P A T H ,i n i t i a l h e a p = 8 0 0 m ) l u c e n e . i n i t V M ( l u c e n e . C L A S S P A T H ,i n i t i a l h e a p = 2 0 0 m ,m a x h e a p = 8 0 0 m )

O resultado que se deve obter, numa consola de Python, semelhante a:


> > >i m p o r t a oL u c e n e > > >l u c e n e . i n i t V M(l u c e n e . C L A S S P A T H) <o b j e t oj c c . J C C E n ve m0 x 8 1 9 2 2 4 0> > > >

Visto como iniciar a mquina virtual, pode-se agora tirar partido de todo o potencial da biblioteca. Vamos comear por criar um indexador, ou seja, um script que crie um indce a partir de uma pasta contendo ficheiros de texto, no formato txt, por uma questo de simplicidade. de ter em ateno que, ao contrrio dos ficheiros txt, os ficheiros como por exemplo os PDF precisam de um parser para os ler, uma vez que ao Lucene alimentado o contedo do ficheiro, e no o ficheiro em si. A lgica por detrs do funcionamento do Lucene j foi explicada anteriormente. Indexador.py
i m p o r tl u c e n e ,o s L u c e n e .i n i t V M(L u c e n e .C L A S S P A T H) #i n i c i a ru m am q u i n av i r t u a l i n d e x P a t h=" T e x t o / I n d e x "#i n d i c a roc a m i n h od ap a s t ac o mo sf i c h e i r o s a n a l y z e r=l u c e n e . S t a n d a r d A n a l y z e r ( )#c r i a roa n a l i s a d o r i n d e x D i r=L u c e n e .F S D i r e c t o r y.G e t D i r e c t o r y(i n d e x P a t h) #l e v a n t a ro uI n d e x I n d e x W r i t e r=L u c e n e .I n d e x W r i t e r(i n d e x D i r,a n a l i s a d o r) #C R I A Ru m ai n d i c a d o r e sE s c r i t o rf a z e r f o rr o o t ,d i r s ,f i l e si no s . w a l k ( ' T e x t o ' ) :#p e r c o r r e m o so sf i c h e i r o sd ap a s t a f o re a c h f i l ei nf i l e s : f i l e i n f o=e a c h f i l e . s p l i t ( ' . ' ) f i l e n a m e='' . j o i n ( f i l e i n f o [ : 1 ] ) i ff i l e i n f o [ 1 ]= =' t x t ' :#P a r aa s s e g u r a rq u es ol e m o sf i c h e i r o sd et e x t os i m p l e s d o c u m e n t=l u c e n e . D o c u m e n t ( )#C r i a m o su md o c u m e n t op r o n t oas e ri n s e r i d on oi n d i c e A d i c i o n a m o soc a m p of a z e rn o m of a af i c h e i r o ,Q u eV a iS e rp o s t e r i o r m e n t ed e v o l v i d ol o sP e s q u i s a sA OU t i l i z a d o r c o n t e n t s=o p e n ( o s . p a t h . j o i n ( r o o t ,e a c h f i l e ) ,' r ' ) . r e a d ( ) C a m p oc o moc o n t e u d of a af i c h e i r o ,t o k e n i z a d oen a oa r m a z e n a d o . i n d e x W r i t e r . a d d D o c u m e n t ( d o c u m e n t )#A d i c i o n aod o c u m e n t oa oi n d i c e i n d e x W r i t e r . c l o s e ( )#F e c h a m o soe s c r i t o r

De seguida, podemos escrever em meia dzia de linhas um pesquisador para comprovarmos que o nosso ndice foi bem construido. No meu exemplo, indexei apenas 2 ficheiros, cada um com a seguinte frase: hello.txt - "Ol Mundo?" goodbye.txt - "Python uma linguagem maravilhosa!" Pesquisador.py
i m p o r t a oL u c e n e l u c e n e . i n i t V M ( l u c e n e . C L A S S P A T H ) d i r e t r i o=L u c e n e .F S D i r e c t o r y.G e t D i r e c t o r y(' t e x t/i n d e x ') #a p o n t a rp a r aaD i r e c t o r i ad ef a z e r n d i c e s e a r c h e r=l u c e n e . I n d e x S e a r c h e r ( d i r e c t o r y )#c r i a rop e s q u i s a d o r a n a l y z e r=l u c e n e . S t a n d a r d A n a l y z e r ( )#c r i a roa n a l i s a d o r t e r m=r a w _ i n p u t ( ' E s c r e v aot e r m oap e s q u i s a r :' )

q u e r y=L u c e n e .Q u e r y P a r s e r(" c o n t e d o ",a n a l i s a d o r).a n a l i s a r(t e r m o) #P a s s a m o so ug a r r a f at r m i c ao ud eo b t e rp a r aQ u e r y P a r s e r ,p a r s u c e s s o s=p e s q u i s a d o r .p e s q u i s a(q u e r y) #O SR e s u l t a d o sR e c u p e r a m o s

i fl e n ( h i t s ) > 0 : r e s u l t a d o s= [s u c e s s o s[x] p a r axn o i n t e r v a l o(l e n(b a t i d a s))] #C r i a m o sU M AL i s t aC O MO SD O C U M E N T O SD O SR E S U L T A D O S n o m e s= [d o c .o b t e r(" f i l e n a m e ") p a r ad o ce mr e s u l t a d o s] #r e c u p e r a m o soc a m p on o m ed eC A D AR e s u l t a d o p o n t u a o= [h i t s .p o n t u a o(x) p a r axn o i n t e r v a l o(l e n(b a t i d a s))] #r e c u p e r a m o su m aA v a l i a d oc o mO p a c oC A D AD o c u m e n t oT e v

wiki.portugal-a-programar.pt/revistaprogramar_arquivo:15_edicao:lucene#conclusao

2/3

18/06/13

Lucene - uma aproximao simples a este poderoso motor de busca [Wiki Portugal-a-Programar]

f o rii nr a n g e ( l e n ( f i l e n a m e s ) ) : p r i n t" % s ,% s "% ( f i l e n a m e s [ i ] ,s c o r e s [ i ] )#D e v o l v e m o so sr e s u l t a d o s e l s e : p r i n t" S e mr e s u l t a d o s ! "

O resultado deste script ser:


j o a o @ j U b u n t u : ~ / D e s k t o p $p y t h o np e s q u i s a d o r . p y E s c r e v aot e r m oap e s q u i s a r :p y t h o n a d e u s ,0 , 5 j o a o @ j U b u n t u : ~ / D e s k t o p $p y t h o np e s q u i s a d o r . p y E s c r e v aot e r m oap e s q u i s a r :h e l l o O l ,0 . 6 2 5 j o a o @ j U b u n t u : ~ / D e s k t o p $p y t h o np e s q u i s a d o r . p y E s c r e v aot e r m oap e s q u i s a r :p o r t u g a l S e mr e s u l t a d o s !

Concluso
A biblioteca Lucene permite ao programador criar rapidamente um motor de busca que pode ser usado como aplicao por si s, ou para ser incorporado noutra, ou num website. Apesar de drasticamente simples, pode tomar contornos bastante complexos medida que se vagueia pelas suas funcionalidades, permitindo uma personalizao e uma costumizao fenomenal, ideal para perfeccionistas que querem lidar com todos os pormenores, ou para aqueles que precisam de um sistema com um determinado conjunto de caractersticas. Para alm disso, grtis, de cdigo livre, de maneira a que para ser usada no precisamos de dispender nenhum tosto e podemos sempre dar uma olhadela ao cdigo por detrs do seu funcionamento para ganhar um maior conhecimento. python , Lucene , programa de revista Voc pode deixar um comentrio, se voc estava conectado pol revistaprogramar_arquivo/15_edicao/lucene.txt Esta pgina foi modificada pela ltima vez em: 2013/02/27 21:09 por Rui Carlos

wiki.portugal-a-programar.pt/revistaprogramar_arquivo:15_edicao:lucene#conclusao

3/3

Você também pode gostar