From: | raul andrez gutierrez alejo <raulandrez(at)gmail(dot)com> |
---|---|
To: | Hellmuth Vargas <hivs77(at)gmail(dot)com> |
Cc: | Lista Postgres ES <pgsql-es-ayuda(at)postgresql(dot)org> |
Subject: | Re: [pgsql-es-ayuda] problema de desempeño con join basado en funcion similaridad |
Date: | 2015-04-24 15:09:43 |
Message-ID: | CAHQFj7255MxdjV6oaHANXi_666QUKQtVzSNmSch6C77uJAQ42w@mail.gmail.com |
Views: | Raw Message | Whole Thread | Download mbox | Resend email |
Thread: | |
Lists: | pgsql-es-ayuda |
Hola Helmith.
un caso parecido lo solucione con un procedimiento almacenado.
en la tabla debe crear 2 campos, una para marca si el registro ya fue
procesado y el otro campo una llave foránea a la misma tabla para marcar a
que registro se parce (registro padra).
en la función primero hace el select del alias "a" con un limite de 100 o
1000 de los registros no procesado, cada registro lo valida contra toda el
tabla de alias "b" y al final actualizo el registro como procesado y el id
del mas parecido, opcional puede guardar el grado de similitud.
esto hace que el problema no sea N*N ejecutado 1 vez, si no 1*N ejecutado N
veces.
el scrip lo ejecute en PHP y final de la ejecución recargaba las misma
pagina y procesaba otros 100 registros, ese navegador lo deje abierto como
2 días y al final termino, como todos los registros de la tabla se van a
actualizar es posible que el tamaño de la tabla se duplique y se debe
ejecutar al finalizar un vacuum full.
el problema yo lo solucione con FTS y cree una columma y su indice de tipo
tsvector, así calcule 1 sola ves el tsvector para toda la tabla y el
tsquery lo calcule en memoria un sola vez por cada registro del alias a.
--
Raul Andres Gutierrez Alejo
El 24 de abril de 2015, 9:16, Hellmuth Vargas <hivs77(at)gmail(dot)com> escribió:
> hola Lista
>
> Tenemos una base con twitter y queremos identificar aquellos que son
> copiados y pegados pero que vendrian a ser el mismo y no se identifican
> como retwitter...por ejemplo tenemos estos dos twitter
>
> Nueva alianza de @ConnectAmericas y @camaracomerbog a disposición de
> empresarios y empresas http://t.co/AQDeppDtso #Noticia
>
> RT @bidcomercio: Nueva alianza de @connectamericas y @camaracomerbog a
> disposición de empresarios y empresas http://t.co/f0Ky2564Lk #Noticia
>
> Ambos son en esencia igual y por medio de la función de similaridad
> (similarity extension pg_trgm) identificamos que poseen una calificación
> 0.725, lo que nos permite concluir que son iguales en esencia. El problema
> surge cuando ya queremos comparar la tabla completa con 2'418.356
> registros aproximadamente (la partición de un mes), pues el join entre
> tablas seria la función de similaridad, la consulta que construí después de
> leer e investigar fue:
>
> SELECT set_limit(0.7);
>
> select a.texto,b.texto,similarity(a.texto,b.texto)
> from particiontwitter.tweets_2015_01 as a
> join particiontwitter.tweets_2015_01 as b on
> a.retweeted_status is NULL and LENGTH(a.texto) > 120
> and b.retweeted_status is NULL and LENGTH(b.texto) > 120
> and a.texto % b.texto
> and a.id<>b.id
>
> tengo los siguiente indices creados relevantes para la consulta:
>
> CREATE INDEX idx_tweets_trgm_2015_01 ON particiontwitter.tweets_2015_01
> USING gin (texto COLLATE pg_catalog."default" gin_trgm_ops);
> CREATE INDEX idx_tweets_trgm_gist_2015_01 ON
> particiontwitter.tweets_2015_01 USING gist (texto COLLATE
> pg_catalog."default" gist_trgm_ops);
> CREATE INDEX idx_tweets_comp3_2015_01 ON particiontwitter.tweets_2015_01
> USING btree (retweeted_status COLLATE pg_catalog."default",
> length(texto::text));
>
> Y el plan de ejecución generado es:
>
> Nested Loop (cost=487.15..485794.60 rows=38938 width=281)
> -> Bitmap Heap Scan on tweets_2015_01 a (cost=487.06..14814.10
> rows=10808 width=148)
> Recheck Cond: ((retweeted_status IS NULL) AND
> (length((text)::text) > 120))
> -> Bitmap Index Scan on idx_tweets_comp3_2015_01
> (cost=0.00..486.52 rows=10808 width=0)
> Index Cond: ((retweeted_status IS NULL) AND
> (length((texto)::text) > 120))
> -> Index Scan using idx_tweets_trgm_gist_2015_01 on tweets_2015_01 b
> (cost=0.08..43.56 rows=4 width=133)
> Index Cond: ((a.texto)::text % (texto)::text)
> Filter: ((retweeted_status IS NULL) AND ((a.id)::text <>
> (id)::text) AND (length((texto)::text) > 120))
>
>
>
> El problema es que no termina!!! lo he dejado correr un día y medio
> sobre solo el mes de enero y no finalizo y supuestamente debemos correrlo
> para todo lo que va el 2015... he intentado con FTS pero tampoco
> funciono... como puedo hacer para optimizar mejor y/o replantear la
> consulta o en general la manera de realizar la comparación que me permita
> obtener resultados en un tiempo menor ? De antemano gracias!!!
>
> -
> Enviado a la lista de correo pgsql-es-ayuda (pgsql-es-ayuda(at)postgresql(dot)org
> )
> Para cambiar tu suscripción:
> http://www.postgresql.org/mailpref/pgsql-es-ayuda
>
>
From | Date | Subject | |
---|---|---|---|
Next Message | Jaime Casanova | 2015-04-28 17:49:39 | Re: Error Funciones y procedimientos |
Previous Message | Hellmuth Vargas | 2015-04-24 14:16:47 | problema de desempeño con join basado en funcion similaridad |