带有Group By和Group Concat的MySQL临时表非常慢

时间:2018-11-26 17:12:30

标签: mysql

我正在尝试构建一个相当简单的临时表。该表将最终为2列:

1个产品ID

2字符串形式的依从性数据,以后可以使用

CREATE TEMPORARY TABLE products.compliances_data
      (INDEX product_id_idx (product_id))
     SELECT
        products.product_id,
        GROUP_CONCAT(JSON_OBJECT('compliance_code', cc.compliance_code, 'compliance_full_name', pc.full_name, 'compliance_web_description_short', pc.web_description_short) SEPARATOR ' - ') as compliances
    FROM products.products products
    LEFT OUTER JOIN products.material_compliance_map cc on products.material_id = cc.material_id
    LEFT OUTER JOIN products.compliances pc on cc.compliance_id = pc.compliance_id
    GROUP BY products.part_number

该表从3个表中收集并连接信息。

  1. 产品表是主要的信息来源。产品表中有一列用于material_id。
  2. material_compiance_map表。这是一个多对多表,可将material_id映射到Compliance_id的
  3. 符合性表。这是存储实际数据的表,我需要从中提取数据以构建级联对象。

问题在于创建临时表需要3-4分钟才能运行,但只能产生大约120万个条目,这似乎非常慢。

对查询的选择部分运行说明将产生: Explain on select image

material_comliance_map中只有642个条目,因此这里没有很多数据需要遍历。

我尝试删除group_concat,这似乎可以将查询速度提高约33%。问题似乎围绕着按声明分组。

构建此临时表时如何提高速度?

编辑:

模式:

material_compliance_map模式

'material_compliance_map'
CREATE TABLE `material_compliance_map` (
  `material_id` int(11) NOT NULL,
  `material_code` varchar(20) COLLATE utf8_unicode_ci NOT NULL,
  `compliance_id` int(11) NOT NULL,
  `compliance_code` varchar(20) COLLATE utf8_unicode_ci NOT NULL,
  PRIMARY KEY (`material_id`,`compliance_id`),
  KEY `fk_compliance_id_material_compliances_compliances` (`compliance_id`),
  KEY `fk_material_id_material_compliances_materials` (`material_id`),
  CONSTRAINT `fk_compliance_id_material_compliances_compliances` FOREIGN KEY (`compliance_id`) REFERENCES `compliances` (`compliance_id`) ON UPDATE CASCADE,
  CONSTRAINT `fk_material_id_material_compliances_materials` FOREIGN KEY (`material_id`) REFERENCES `materials` (`material_id`) ON UPDATE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci

合规模式:

'compliances'
CREATE TABLE `compliances` (
  `compliance_id` int(11) NOT NULL AUTO_INCREMENT,
  `compliance_code` varchar(20) NOT NULL,
  `full_name` varchar(155) DEFAULT NULL,
  `web_description_short` varchar(45) DEFAULT NULL,
  PRIMARY KEY (`compliance_id`),
  UNIQUE KEY `compliance_id_UNIQUE` (`compliance_id`),
  UNIQUE KEY `compliance_code_UNIQUE` (`compliance_code`)
) ENGINE=InnoDB AUTO_INCREMENT=15 DEFAULT CHARSET=latin1

产品架构:

'products' 

CREATE TABLE `products` (
 `part_number` varchar(27) NOT NULL,
  `material_code` varchar(30) DEFAULT NULL,
  `material_id` int(11) DEFAULT NULL,
  `size_code` varchar(15) DEFAULT NULL,
  `size_id` int(11) DEFAULT NULL,
  `erp_description_1` varchar(31) DEFAULT NULL,
  `erp_description_2` varchar(31) DEFAULT NULL,
  `search_description` varchar(250) DEFAULT NULL,
  `weight_lbs` decimal(8,4) DEFAULT NULL,
  `part_number_prefix` varchar(15) DEFAULT NULL,
  `tight_tolerance` tinyint(4) DEFAULT NULL,
  `product_id` int(11) NOT NULL AUTO_INCREMENT,
  PRIMARY KEY (`product_id`),
  UNIQUE KEY `part_number_UNIQUE` (`part_number`),
  UNIQUE KEY `product_id_UNIQUE` (`product_id`),
  KEY `fk_material_id_products_materials` (`material_id`),
  KEY `fk_size_id_products_sizes` (`size_id`),
  KEY `product_id` (`product_id`),
  KEY `size_id_idx` (`size_id`),
  KEY `size_id_productsidx` (`size_id`),
  KEY `material_id_idx` (`material_id`),
  CONSTRAINT `fk_material_id_products_materials` FOREIGN KEY (`material_id`) REFERENCES `materials` (`material_id`),
  CONSTRAINT `fk_size_id_products_sizes` FOREIGN KEY (`size_id`) REFERENCES `sizes` (`size_id`)
) ENGINE=InnoDB AUTO_INCREMENT=1140987 DEFAULT CHARSET=latin1

0 个答案:

没有答案