2016-08-15 4 views
-4

로드 소요 시간 60 초, 어떻게 최적화 할 수 있습니까?MySQL에서 뷰를 최적화하는 방법은 무엇입니까?

설명 구조체 :

explain tablename; 

IMG : http://i.stack.imgur.com/TfbY3.png

설명 SQL

explain select * from tablename; 

IMG : http://i.stack.imgur.com/jHI47.png

REAL DB

DROP TABLE IF EXISTS `afiliados`; 
CREATE TABLE `afiliados` (
    `id_afiliado` int(10) NOT NULL AUTO_INCREMENT, 
    `clave_panel` char(15) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `clave_panel_ask` datetime DEFAULT NULL, 
    `id_trabajador` char(20) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `persona` char(1) COLLATE latin1_spanish_ci DEFAULT 'H', 
    `Estado` int(10) NOT NULL DEFAULT '0', 
    `doc_fiscal` int(10) DEFAULT NULL, 
    `id_fiscal` char(20) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Nombre` char(25) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Apellidos` char(50) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `fecha_nacimiento` datetime DEFAULT NULL, 
    `Telefono Principal` char(12) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Telefono Secundario` char(12) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Fecha_Alta` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP, 
    `Fecha_Aprobacion` datetime DEFAULT NULL, 
    `id_cuenta_aprobacion` int(11) DEFAULT NULL, 
    `Fecha_Documentacion` datetime DEFAULT NULL, 
    `Fecha_Alta_Sindicato` datetime DEFAULT NULL, 
    `Fecha_Baja_Sindicato` datetime DEFAULT NULL, 
    `Motivo_Baja_Sindicato` char(255) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Fecha_Desafiliacion` char(255) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Fax` char(12) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Direccion` char(100) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `CP` char(5) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Ciudad` char(35) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Provincia` char(25) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Pais` char(2) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Nacionalidad` char(2) COLLATE latin1_spanish_ci NOT NULL DEFAULT '', 
    `Email` char(50) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Email_secundario` char(50) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Id_delegado` int(10) DEFAULT NULL, 
    `Comentario` char(255) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Interno` char(255) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Eliminado` tinyint(1) NOT NULL DEFAULT '0', 
    `Es_Delegado` tinyint(1) NOT NULL DEFAULT '0', 
    `id_cuenta` int(10) DEFAULT NULL, 
    `Fecha_mod` datetime DEFAULT NULL, 
    `mod_id_cuenta` int(10) DEFAULT NULL, 
    `noemail` tinyint(1) NOT NULL DEFAULT '0', 
    `noemail_public` tinyint(1) NOT NULL DEFAULT '0', 
    `noemail_fact` tinyint(1) NOT NULL DEFAULT '0', 
    `noti_alta` datetime DEFAULT NULL, 
    `noti_fact` datetime DEFAULT NULL, 
    `noti_baja` datetime DEFAULT NULL, 
    `fecha_star_facturacion` datetime DEFAULT NULL, 
    `fecha_proxima_facturacion` datetime DEFAULT NULL, 
    `ciclo_mensual_facturacion` int(10) unsigned NOT NULL DEFAULT '3', 
    `fecha_sync` datetime DEFAULT NULL, 
    `fecha_chk` datetime DEFAULT NULL, 
    `LOPD` tinyint(1) NOT NULL DEFAULT '0', 
    `ncarnet` int(10) DEFAULT NULL, 
    `id_caja` int(10) unsigned NOT NULL DEFAULT '0', 
    `caja_fecha_add` datetime DEFAULT NULL, 
    `id_cuenta_caja_add` int(10) DEFAULT '0', 
    `caja_fecha_del` datetime DEFAULT NULL, 
    `id_cuenta_caja_del` int(10) DEFAULT '0', 
    PRIMARY KEY (`id_afiliado`), 
    KEY `apellidos` (`Apellidos`), 
    KEY `Email` (`Email`), 
    KEY `es_delegado` (`Es_Delegado`), 
    KEY `id_caja` (`id_caja`), 
    KEY `id_cuenta` (`id_cuenta`), 
    KEY `id_delegado` (`Id_delegado`), 
    KEY `id_fiscal` (`id_fiscal`), 
    KEY `id_trabajador` (`id_trabajador`), 
    KEY `nombre` (`Nombre`) 
) ENGINE=MyISAM AUTO_INCREMENT=4467 DEFAULT CHARSET=latin1 COLLATE=latin1_spanish_ci ROW_FORMAT=DYNAMIC; 



INSERT INTO `afiliados` VALUES (194,NULL,NULL,'XXXXX','M',1,1,'XXXXX','Frank','Poland','1967-11-13 00:00:00','0000000','','2012-08-08 10:35:31','2012-08-08 21:05:59',0,'2012-08-09 00:00:00','2005-04-04 00:00:00',NULL,NULL,NULL,'','Adress','00000','Sevilla','Sevilla','es','es',NULL,NULL,NULL,NULL,NULL,0,0,NULL,NULL,NULL,0,0,0,NULL,NULL,NULL,NULL,NULL,3,NULL,NULL,0,NULL,0,NULL,NULL,NULL,NULL); 




DROP TABLE IF EXISTS `contratos`; 
CREATE TABLE `contratos` (
    `Id_contrato` int(10) NOT NULL AUTO_INCREMENT, 
    `id_empresa` int(10) DEFAULT NULL, 
    `Marca` char(255) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Departamento` char(255) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Localizacion` char(255) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `fecha_baja` datetime DEFAULT NULL, 
    `id_cuenta_add` int(10) DEFAULT NULL, 
    PRIMARY KEY (`Id_contrato`), 
    KEY `id_empresa` (`id_empresa`) 
) ENGINE=MyISAM AUTO_INCREMENT=1013 DEFAULT CHARSET=latin1 COLLATE=latin1_spanish_ci ROW_FORMAT=FIXED; 



INSERT INTO `contratos` VALUES (38,7,'Telefonica','CAOL','2º Planta',NULL,NULL),(193,11,'Vodafone','Atencion al Cliente','Planta Baja/1ª Planta',NULL,3); 


DROP TABLE IF EXISTS `empresa`; 
CREATE TABLE `empresa` (
    `Id_empresa` int(10) NOT NULL AUTO_INCREMENT, 
    `cif` char(10) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Razon_Social` char(60) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `empresa` char(40) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Centro` char(40) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `Provincia` char(30) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `localizacion_sindicato` char(100) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `id_setting` int(10) DEFAULT NULL, 
    `direccion` char(100) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `cp` char(5) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `ciudad` char(30) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `id_cuenta_add` int(10) unsigned DEFAULT '0', 
    `fecha_baja` datetime DEFAULT NULL, 
    `id_cuenta_baja` int(10) unsigned DEFAULT NULL, 
    PRIMARY KEY (`Id_empresa`), 
    KEY `cif` (`cif`), 
    KEY `empresa` (`empresa`), 
    KEY `id_setting` (`id_setting`) 
) ENGINE=MyISAM AUTO_INCREMENT=871 DEFAULT CHARSET=latin1 COLLATE=latin1_spanish_ci ROW_FORMAT=FIXED; 



INSERT INTO `empresa` VALUES (7,'A78751997','ATENTO TELESERVICIOS, S.A.','Atento','Indotorre','Sevilla','2º Planta',13,NULL,NULL,NULL,0,NULL,NULL),(11,'B62916077','KONECTA BTO, S.L.','Konecta BTO','Prado de la Torre','Sevilla','1ª Planta (Pasillo Baño)',19,'Prado de la Torre s/n','41110','Bollulos',0,NULL,NULL); 


DROP TABLE IF EXISTS `historico`; 
CREATE TABLE `historico` (
    `Id_historico` int(10) NOT NULL AUTO_INCREMENT, 
    `id_afiliado` int(10) DEFAULT NULL, 
    `fecha_alta` datetime DEFAULT NULL, 
    `tipo_contrato` smallint(5) DEFAULT NULL COMMENT 'Obra y Servicio ,etc ....', 
    `fecha_baja` datetime DEFAULT NULL, 
    `motivo_baja` smallint(5) DEFAULT NULL, 
    `fecha_provision` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP, 
    `id_contrato` int(10) DEFAULT NULL, 
    `comentario` char(255) COLLATE latin1_spanish_ci DEFAULT NULL, 
    `id_cuenta` int(10) DEFAULT NULL, 
    `Fecha_mod` datetime DEFAULT NULL, 
    `mod_id_cuenta` int(10) DEFAULT NULL, 
    PRIMARY KEY (`Id_historico`), 
    KEY `id_afiliado` (`id_afiliado`), 
    KEY `id_contrato` (`id_contrato`), 
    KEY `id_cuenta` (`id_cuenta`), 
    KEY `tipo_contrato` (`tipo_contrato`) 
) ENGINE=MyISAM AUTO_INCREMENT=4814 DEFAULT CHARSET=latin1 COLLATE=latin1_spanish_ci ROW_FORMAT=FIXED; 



INSERT INTO `historico` VALUES (227,194,'2005-04-04 00:00:00',0,'2014-01-01 00:00:00',-1,'2012-08-08 10:35:47',38,'',16,NULL,NULL),(1586,194,'2014-01-01 00:00:00',0,NULL,NULL,'2015-08-24 21:14:41',193,'',115,NULL,NULL); 

조회 수 :

DROP VIEW IF EXISTS `detalle_full_ko`; 
CREATE VIEW `detalle_full_ko` AS 
select `afiliados`.`id_afiliado` AS `Id_afiliado`,`afiliados`.`ncarnet` AS `ncarnet`, 
     `afiliados`.`Id_delegado` AS `Id_delegado`,`afiliados`.`Fecha_Alta` AS `Fecha_Alta_Afiliado`, 
     `afiliados`.`id_trabajador` AS `id_trabajador`,`afiliados`.`persona` AS `persona`, 
     `afiliados`.`Nombre` AS `Nombre`,`afiliados`.`Apellidos` AS `Apellidos`, 
     `afiliados`.`id_fiscal` AS `id_fiscal`,`afiliados`.`Email` AS `Email`, 
     `afiliados`.`Email_secundario` AS `Email_secundario`, 
     `afiliados`.`noemail` AS `noemail`,`afiliados`.`noemail_public` AS `noemail_public`, 
     `afiliados`.`Telefono Principal` AS `Telefono Principal`, 
     `afiliados`.`Telefono Secundario` AS `Telefono Secundario`, 
     `afiliados`.`Fax` AS `Fax`,`afiliados`.`Ciudad` AS `Ciudad`, 
     `afiliados`.`CP` AS `CP`,`afiliados`.`Provincia` AS `Provincia_Afiliado`, 
     `afiliados`.`fecha_nacimiento` AS `fecha_nacimiento`, 
     `afiliados`.`Estado` AS `Estado`,`afiliados`.`Es_Delegado` AS `Es_Delegado`, 
     `afiliados`.`Eliminado` AS `Eliminado`,`detalle_historico_ko`.`fecha_alta` AS `Fecha_Alta_Empresa`, 
     `empresa`.`Razon_Social` AS `Razon_Social`,`empresa`.`empresa` AS `nombre_empresa`, 
     `empresa`.`Centro` AS `Centro`,`contratos`.`Departamento` AS `Departamento`, 
     `contratos`.`Marca` AS `Marca`,`empresa`.`Provincia` AS `Provincia`, 
     `empresa`.`localizacion_sindicato` AS `localizacion_sindicato`, 
     `detalle_historico_ko`.`Id_contrato` AS `id_contrato`, 
     `contratos`.`id_empresa` AS `id_empresa`,`detalle_historico_ko`.`tipo_contrato` AS `tipo_contrato`, 
     `afiliados`.`Fecha_Alta_Sindicato` AS `Fecha_Alta_Sindicato`, 
     `afiliados`.`Fecha_Baja_Sindicato` AS `Fecha_Baja_Sindicato`, 
     `afiliados`.`fecha_sync` AS `fecha_sync`,`afiliados`.`noti_alta` AS `noti_alta`, 
     `afiliados`.`noti_fact` AS `noti_fact`,`afiliados`.`noti_baja` AS `noti_baja`, 
     `afiliados`.`Fecha_mod` AS `Fecha_mod`,`afiliados`.`LOPD` AS `LOPD` 
    from (((`contratos` 
          join `empresa` on((`empresa`.`Id_empresa` = `contratos`.`id_empresa`))) 
        join `detalle_historico_ko` on(((`empresa`.`Id_empresa` = `detalle_historico_ko`.`Id_empresa`) 
             and (`contratos`.`Id_contrato` = `detalle_historico_ko`.`Id_contrato`)))) 
      join `afiliados` on((`detalle_historico_ko`.`id_afiliado` = `afiliados`.`id_afiliado`)) 
     ) 
    where (`afiliados`.`LOPD` = 0) 
    group by `afiliados`.`id_afiliado`; 


DROP VIEW IF EXISTS `detalle_full_ok`; 
CREATE VIEW `detalle_full_ok` AS 
select `afiliados`.`id_afiliado` AS `Id_afiliado`,`afiliados`.`ncarnet` AS `ncarnet`, 
     `afiliados`.`Id_delegado` AS `Id_delegado`,`afiliados`.`Fecha_Alta` AS `Fecha_Alta_Afiliado`, 
     `afiliados`.`id_trabajador` AS `id_trabajador`,`afiliados`.`persona` AS `persona`, 
     `afiliados`.`Nombre` AS `Nombre`,`afiliados`.`Apellidos` AS `Apellidos`, 
     `afiliados`.`id_fiscal` AS `id_fiscal`,`afiliados`.`Email` AS `Email`, 
     `afiliados`.`Email_secundario` AS `Email_secundario`, 
     `afiliados`.`noemail` AS `noemail`,`afiliados`.`noemail_public` AS `noemail_public`, 
     `afiliados`.`Telefono Principal` AS `Telefono Principal`, 
     `afiliados`.`Telefono Secundario` AS `Telefono Secundario`, 
     `afiliados`.`Fax` AS `Fax`,`afiliados`.`Ciudad` AS `Ciudad`, 
     `afiliados`.`CP` AS `CP`,`afiliados`.`Provincia` AS `Provincia_Afiliado`, 
     `afiliados`.`fecha_nacimiento` AS `fecha_nacimiento`, 
     `afiliados`.`Estado` AS `Estado`,`afiliados`.`Es_Delegado` AS `Es_Delegado`, 
     `afiliados`.`Eliminado` AS `Eliminado`,`detalle_historico_ok`.`fecha_alta` AS `Fecha_Alta_Empresa`, 
     `empresa`.`Razon_Social` AS `Razon_Social`,`empresa`.`empresa` AS `nombre_empresa`, 
     `empresa`.`Centro` AS `Centro`,`contratos`.`Departamento` AS `Departamento`, 
     `contratos`.`Marca` AS `Marca`,`empresa`.`Provincia` AS `Provincia`, 
     `empresa`.`localizacion_sindicato` AS `localizacion_sindicato`, 
     `detalle_historico_ok`.`Id_contrato` AS `id_contrato`, 
     `contratos`.`id_empresa` AS `id_empresa`,`detalle_historico_ok`.`tipo_contrato` AS `tipo_contrato`, 
     `afiliados`.`Fecha_Alta_Sindicato` AS `Fecha_Alta_Sindicato`, 
     `afiliados`.`Fecha_Baja_Sindicato` AS `Fecha_Baja_Sindicato`, 
     `afiliados`.`fecha_sync` AS `fecha_sync`,`afiliados`.`noti_alta` AS `noti_alta`, 
     `afiliados`.`noti_fact` AS `noti_fact`,`afiliados`.`noti_baja` AS `noti_baja`, 
     `afiliados`.`Fecha_mod` AS `Fecha_mod`,`afiliados`.`LOPD` AS `LOPD` 
    from (((`contratos` 
          join `empresa` on((`empresa`.`Id_empresa` = `contratos`.`id_empresa`))) 
        join `detalle_historico_ok` on(((`empresa`.`Id_empresa` = `detalle_historico_ok`.`Id_empresa`) 
             and (`contratos`.`Id_contrato` = `detalle_historico_ok`.`Id_contrato`)))) 
      join `afiliados` on((`detalle_historico_ok`.`id_afiliado` = `afiliados`.`id_afiliado`)) 
     ) 
    where (`afiliados`.`LOPD` = 0) 
    group by `afiliados`.`id_afiliado`; 



DROP VIEW IF EXISTS `detalle_historico_ko`; 
CREATE VIEW `detalle_historico_ko` AS 
select high_priority `historico`.`Id_historico` AS `Id_historico`, 
     `historico`.`id_afiliado` AS `id_afiliado`,`contratos`.`Id_contrato` AS `Id_contrato`, 
     `historico`.`fecha_provision` AS `fecha_provision`,`empresa`.`Id_empresa` AS `Id_empresa`, 
     `empresa`.`empresa` AS `Empresa`,`empresa`.`Provincia` AS `Provincia`, 
     `empresa`.`Centro` AS `Centro`,`contratos`.`Marca` AS `Marca`, 
     `contratos`.`Departamento` AS `Departamento`,`historico`.`fecha_alta` AS `fecha_alta`, 
     `historico`.`fecha_baja` AS `fecha_baja`,`historico`.`comentario` AS `comentario`, 
     `historico`.`tipo_contrato` AS `tipo_contrato` 
    from (`empresa` 
      join (`contratos` 
        join `historico` on((`contratos`.`Id_contrato` = `historico`.`id_contrato`))) on((`empresa`.`Id_empresa` = `contratos`.`id_empresa`)) 
     ) 
    group by `historico`.`id_afiliado` 
    order by isnull(`historico`.`fecha_baja`) desc,`historico`.`fecha_baja` desc; 



DROP VIEW IF EXISTS `detalle_historico_ok`; 
CREATE VIEW `detalle_historico_ok` AS 
select high_priority `historico`.`Id_historico` AS `Id_historico`, 
     `historico`.`id_afiliado` AS `id_afiliado`,`contratos`.`Id_contrato` AS `Id_contrato`, 
     `historico`.`fecha_provision` AS `fecha_provision`,`empresa`.`Id_empresa` AS `Id_empresa`, 
     `empresa`.`empresa` AS `Empresa`,`empresa`.`Provincia` AS `Provincia`, 
     `empresa`.`Centro` AS `Centro`,`contratos`.`Marca` AS `Marca`, 
     `contratos`.`Departamento` AS `Departamento`,`historico`.`fecha_alta` AS `fecha_alta`, 
     `historico`.`fecha_baja` AS `fecha_baja`,`historico`.`comentario` AS `comentario`, 
     `historico`.`tipo_contrato` AS `tipo_contrato` 
    from (`empresa` 
      join (`contratos` 
        join `historico` on((`contratos`.`Id_contrato` = `historico`.`id_contrato`))) on((`empresa`.`Id_empresa` = `contratos`.`id_empresa`)) 
     ) 
    group by `historico`.`Id_historico`,`historico`.`id_afiliado` 
    order by isnull(`historico`.`fecha_baja`) desc,`historico`.`fecha_baja` desc; 

는 SELECT는 보기 모두 잘 가고 있지만, SELECT 경우 detalle_full_ko 보기가 잘못 detalle_full_ok합니다.

보기 보기 detalle_full_ok은 느리고 detalle_full_ko 보기 빠릅니다. 문제는 입니다. detalle_full_ko를 참조하십시오. 잘못된 검색 nombre_empresa 필드.

행 : afiliados (4700) Empresa 연락처 (800) contratos (4700)

+0

카디널리티 테이블을 추가하십시오 – Gar

+0

'CHAR'을'VARCHAR'로 변경하십시오. 각 테이블의 행 수는 몇 개입니까? 각 테이블에 대해'SHOW CREATE TABLE'을 제공하십시오. 'SHOW CREATE VIEW'을 제공해주십시오. –

+0

질문을 db 코드 – javi200482

답변

0

먼저 쿼리를 깎다 만 historico를 얻을 수 있습니다. Id_historicohistorico. id_afiliado. 즉, 그냥 원하는 ID 쌍을 얻는 데 필요하지 않은 열 및 테이블 피하기된다

SELECT DISTINCT Id_historico, id_afiliado 
    FROM ... 
    -- no GROUP BY or ORDER BY 

그런 다음 사용을 그 하위 쿼리는 데이터의 나머지 얻을 같이 그러나

SELECT lots-of-stuff 
    FROM (the above select) 
    JOIN back to all the tables 
    WHERE ... 
    GROUP BY -- probably needed again? 
    ORDER BY ... 

을, GROUP BY에는 SELECT의 모든 비 집계 값이 포함되어 있지 않으므로 '부적절한'것이므로 ONLY_FULL_GROUP_BY으로 오류로 표시 될 수 있습니다.

+0

아니요, 모든 열이 필요합니다.이 뷰를 다른 스크립트에서 실행하고 각 스크립트는 모두 또는 일부 열을 가져 오십시오. 문제는 "detalle_full_ok" 가 나는 "DISTINCT Id_historico, id_afiliado 선택"사용 canot "히스토리"의 첫 번째 행을 얻을 "detalle_full_ok" "히스토리"의 올바른 행을 얻고있다 DISTINCT 같은 행을 얻을 id_historico 때문에 고유하고 id_afiliado가 중복 됨 감사하지만 작동하지 않음 – javi200482

관련 문제