MySQL - Optimizar una consulta

 
Vista:
Imágen de perfil de Lina
Val: 10
Ha aumentado su posición en 9 puestos en MySQL (en relación al último mes)
Gráfica de MySQL

Optimizar una consulta

Publicado por Lina (5 intervenciones) el 20/04/2017 17:37:31
Hola, gente, necesito ayuda para optimizar una consulta, tarda + de 30seg

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
SELECT
	LPAD(a.id,6,0) as id2,a.id,a.cif,CONCAT('link:clientes(',-a.id,'):',a.nombre) nombre,
	a.id action_id, CONCAT(LPAD(a.id,6,0),' - ',a.nombre) action_title,a.nombre nombre2,
	x.nombre_pais pais,x.nombre_provincia provincia,x.nombre_poblacion poblacion,x.nombre_codpostal codpostal,x.direccion direccion,
	(SELECT y1.valor FROM tbl_comunicaciones y1 WHERE  y1.id=(SELECT id FROM tbl_comunicaciones WHERE id_direccion=x.id AND id_tipocom=(SELECT id FROM tbl_tiposcom WHERE codigo='phone')LIMIT 1)) tel_fijo,
	(SELECT y2.valor FROM tbl_comunicaciones y2 WHERE  y2.id=(SELECT id FROM tbl_comunicaciones WHERE id_direccion=x.id AND id_tipocom=(SELECT id FROM tbl_tiposcom WHERE codigo='movil')LIMIT 1)) tel_movil,
	(SELECT y5.valor FROM tbl_comunicaciones y5 WHERE  y5.id=(SELECT id FROM tbl_comunicaciones WHERE id_direccion=x.id AND id_tipocom=(SELECT id FROM tbl_tiposcom WHERE codigo='email')LIMIT 1)) email,
	c.nombre groupclient,
	CASE (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_view,
	CASE (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_edit,
	CASE (1=1) OR (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_vcard,
	CASE (1=1) OR (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_qrcode,
	CASE (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_pdf2filter,
	CASE (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_view2filter,
	CASE (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_delete
FROM  tbl_clientes a
LEFT JOIN tbl_direcciones x ON x.id=(SELECT id FROM tbl_direcciones WHERE id_aplicacion='1' AND id_registro=a.id ORDER BY seleccion DESC, id ASC LIMIT 1)
LEFT JOIN tbl_gruposclientes c ON a.id_grupoc = c.id
WHERE (1) AND (id_campanya='' OR ''='') AND (id_importacion='' OR ''='') AND (1=1)
Valora esta pregunta
Me gusta: Está pregunta es útil y esta claraNo me gusta: Está pregunta no esta clara o no es útil
0
Responder
Imágen de perfil de Lina
Val: 10
Ha aumentado su posición en 9 puestos en MySQL (en relación al último mes)
Gráfica de MySQL

Optimizar una consulta

Publicado por Lina (5 intervenciones) el 20/04/2017 18:49:30
Hice una tabla deriva, pero se demora lo mismo


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
SELECT 	id2,ida,cif,CONCAT('link:clientes(',-ida,'):',nombrea) nombre,
	ida action_id, CONCAT(LPAD(ida,6,0),' - ',nombrea) action_title,
	nombrea nombre2,
 
	pais,provincia,poblacion,codpostal,direccion,
 
	CONCAT('tel:',tel_fijo) tel_fijo,
	CONCAT('tel:',tel_movil) tel_movil,
	CONCAT('mailto:',email) email,
	groupclient,CONCAT('cbox:clientes') tree,
 
	CASE (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_view,
	CASE (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_edit,
	CASE (1=1) OR (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_vcard,
	CASE (1=1) OR (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_qrcode,
	CASE (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_pdf2filter,
	CASE (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_view2filter,
	CASE (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_delete
 
FROM (	SELECT LPAD(a.id,6,0) as id2,a.id as ida,a.nombre nombrea,a.cif,
 
	x.nombre_pais pais,x.nombre_provincia provincia,x.nombre_poblacion poblacion,x.nombre_codpostal codpostal,x.direccion direccion,
 
	(SELECT y1.valor FROM tbl_comunicaciones y1 WHERE  y1.id=(SELECT id FROM tbl_comunicaciones WHERE id_direccion=x.id AND id_tipocom=(SELECT id FROM tbl_tiposcom WHERE codigo='phone')LIMIT 1)) tel_fijo,
	(SELECT y2.valor FROM tbl_comunicaciones y2 WHERE  y2.id=(SELECT id FROM tbl_comunicaciones WHERE id_direccion=x.id AND id_tipocom=(SELECT id FROM tbl_tiposcom WHERE codigo='movil')LIMIT 1)) tel_movil,
	(SELECT y5.valor FROM tbl_comunicaciones y5 WHERE  y5.id=(SELECT id FROM tbl_comunicaciones WHERE id_direccion=x.id AND id_tipocom=(SELECT id FROM tbl_tiposcom WHERE codigo='email')LIMIT 1)) email,
 
	c.nombre groupclient,
 
	a.id_campanya,a.id_importacion
	FROM
	tbl_clientes a
	INNER JOIN tbl_gruposclientes c ON a.id_grupoc = c.id
	INNER JOIN tbl_direcciones x ON x.id=(SELECT id FROM tbl_direcciones WHERE id_aplicacion='1' AND id_registro=a.id ORDER BY seleccion DESC, id ASC LIMIT 1)
)Z
 
WHERE (1) AND (id_campanya='' OR ''='') AND (id_importacion='' OR ''='') AND (1=1)

alguna idea? :(
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
0
Comentar
sin imagen de perfil
Val: 953
Oro
Ha mantenido su posición en MySQL (en relación al último mes)
Gráfica de MySQL

Optimizar una consulta

Publicado por leonardo_josue (414 intervenciones) el 20/04/2017 19:58:23
Hola Lina:

Desde mi punto de vista estás haciendo demasiadas subconsultas y comparaciones que realmente son inútiles, sin embargo, para poder indicarte alguna otra alternativa para mejora la consulta necesitaríamos que postearas la estructura de tus tablas y que nos pusieras algunos datos de ejemplo... a partir de esos datos dinos qué es lo que esperas como resultado y así podremos indicarte alguna otra alternativa.

Ahora bien, de entrada te comento lo siguiente:

1. Haces demasiadas consultas del mismo tipo, con LIMIT 1 al final... supongo que esto lo haces porque tienes una relación 1 a muchos entre tus tablas y quieres mostrar un sólo registro... esta técnica no es efectiva cuando tienes tantas subconsultas y puede ser la principal razón de que se tarde tanto... hay otra formas para hacer lo mismo utilizando JOINS simples y numerando tus registros, pero insisto en que necesitaríamos conocer tu modelo para darte otra alternativa:

2. Tienes condiciones completamente inútiles, por ejemplo en los CASE-WHEN,por ejemplo al poner esto:

1
CASE (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_view,

la condición siempre será 1 por lo tanto es igual a que pusieras esto:

1
'true' action_view,

Más que tratar de "optimizar" tu consulta, deberías pensar en cambiarla por completo.

Saludos
Leo.
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
1
Comentar
Imágen de perfil de consulta
Val: 10
Ha aumentado su posición en 9 puestos en MySQL (en relación al último mes)
Gráfica de MySQL

Optimizar una consulta

Publicado por consulta (5 intervenciones) el 20/04/2017 22:22:22
Hola,

Muchas gracias por tus comentarios revise a fondo mi consulta (parte por parte) y encontré que lo que la hacia demorar era esta parte:

1
INNER JOIN tbl_direcciones x ON x.id=(SELECT id FROM tbl_direcciones WHERE id_aplicacion='1' AND id_registro=a.id ORDER BY seleccion DESC, id ASC LIMIT 1)

Como dijiste el select anidado tardaba bastante así que lo cambie por:

1
2
LEFT JOIN tbl_direcciones x ON x.id_registro=a.id
WHERE x.id_aplicacion='1'

y se corrio en 5 segundos,con los mismos resultados :D

por otro lado en el caso de los
CASE (1=1) WHEN 1 THEN 'true' ELSE 'false' END action_pdf2filter
el (1=1) son variables enviadas por php
(CASE ($varible1=$varible2) WHEN 1 THEN 'true' ELSE 'false' END action_pdf2filter)
por lo tanto no van a ser iguales siempre.

Muchas gracias, solucionado.
Valora esta respuesta
Me gusta: Está respuesta es útil y esta claraNo me gusta: Está respuesta no esta clara o no es útil
1
Comentar