【发布时间】:2019-06-26 02:35:54
【问题描述】:
这是我的 SQL(带解释):
EXPLAIN
UPDATE
VF_KRED kred
INNER JOIN GBI gbi ON
kred.vendor = gbi.vendor
INNER JOIN MASTER_DATA master_data ON
master_data.vendor_code = gbi.vendor
SET
kred.GBI_VAL_REP =
(CASE
WHEN kred.country = 'JP' THEN
CASE
WHEN gbi.WITHHOLD_TAX_CODE = 0 THEN 2
WHEN gbi.WITHHOLD_TAX_CODE = 'IN' THEN 1
END
ELSE
CASE
WHEN gbi.WITHHOLD_TAX_CODE = master_data.REDUCED_RATE THEN
CASE
WHEN gbi.WITHHOLD_TAX_CODE = 0 THEN 3
WHEN gbi.WITHHOLD_TAX_CODE BETWEEN 1 AND 19 THEN 4
END
ELSE 5
END
END);
给出以下结果:
现在,UPDATE SQL 需要大约 6 分钟以上的时间。
以下是表的索引:
- VF_KRED 表:
- GBI 表:
- MASTER_DATA 表:
VENDOR 列都是varchar(25) 类型。
-- 编辑:(在下面描述整个表结构):
SHOW CREATE TABLE GBI;
CREATE TABLE `GBI` (
`VENDOR` varchar(25) CHARACTER SET utf8 NOT NULL,
`COMPANY_CODE` varchar(5) CHARACTER SET latin1 NOT NULL DEFAULT '',
`VENDOR_NAME` varchar(100) CHARACTER SET utf8 NOT NULL DEFAULT '',
`WITHHOLD_TAX_TYPE` varchar(2) CHARACTER SET latin1 NOT NULL DEFAULT '',
`WITHHOLD_TAX_CODE` varchar(2) CHARACTER SET latin1 NOT NULL DEFAULT '',
`DOCUMENT_CURRENCY` varchar(4) CHARACTER SET latin1 NOT NULL DEFAULT '',
`CREATE_DT` datetime NOT NULL,
PRIMARY KEY (`VENDOR`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci
SHOW CREATE TABLE VF_KRED;
CREATE TABLE `VF_KRED` (
`VENDOR` varchar(25) CHARACTER SET latin1 NOT NULL,
`COUNTRY_CODE` varchar(5) CHARACTER SET latin1 DEFAULT NULL,
`COUNTRY` varchar(3) CHARACTER SET latin1 DEFAULT NULL,
`SEARCH_TERM` varchar(100) CHARACTER SET latin1 DEFAULT NULL,
`CREATE_DT` datetime DEFAULT NULL,
`GBI_VAL_REP` int(11) NOT NULL DEFAULT 5,
PRIMARY KEY (`VENDOR`),
KEY `vf_kred` (`GBI_VAL_REP`),
KEY `VF_KRED_COUNTRY_IDX` (`COUNTRY`) USING BTREE,
CONSTRAINT `vf_kred_ibfk_1` FOREIGN KEY (`GBI_VAL_REP`) REFERENCES `VENDOR_RATE_CATEGORY` (`ID`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci
SHOW CREATE TABLE MASTER_DATA;
CREATE TABLE `MASTER_DATA` (
`ID` int(11) NOT NULL AUTO_INCREMENT,
`VENDOR_CODE` varchar(25) CHARACTER SET latin1 DEFAULT NULL,
`VENDOR_NAME` varchar(2000) CHARACTER SET latin1 DEFAULT NULL,
`COUNTRY` varchar(2) CHARACTER SET latin1 DEFAULT NULL,
`APPLN_RECEIVED_FROM_US` datetime DEFAULT NULL,
`ITUNES_CONTRACT_NUM` varchar(2000) CHARACTER SET latin1 DEFAULT NULL,
`CONTRACT_EFFECTIVE_DT` datetime DEFAULT NULL,
`CONTRACT_EXPIRATION_DT` datetime DEFAULT NULL,
`AUTO_RENEWAL` varchar(10) CHARACTER SET latin1 DEFAULT NULL,
`REDUCED_RATE` int(11) DEFAULT NULL,
`FORM_17` varchar(45) CHARACTER SET latin1 DEFAULT NULL,
`RESIDENCY_CERT_ISSUE_DT` datetime DEFAULT NULL,
`TAX_AUTHORITY_SUBMISSION_DT` datetime DEFAULT NULL,
`TAX_AUTHORITY_ACCEPTANCE_DT` datetime DEFAULT NULL,
`STATUS` varchar(45) CHARACTER SET latin1 DEFAULT NULL,
`FORM_17_EXPIRATION` varchar(45) CHARACTER SET latin1 DEFAULT NULL,
`COMMENTS` varchar(2000) CHARACTER SET latin1 DEFAULT NULL,
`REMARKS` varchar(2000) CHARACTER SET latin1 DEFAULT NULL,
`CATEGORY` varchar(45) CHARACTER SET latin1 DEFAULT NULL,
PRIMARY KEY (`ID`),
KEY `MASTER_DATA_VENDOR_CODE_IDX` (`VENDOR_CODE`) USING BTREE
) ENGINE=InnoDB AUTO_INCREMENT=2369 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci
有什么线索吗?
【问题讨论】:
-
请为两张表提供
SHOW CREATE TABLE。他们会暴露一个问题。innodb_buffer_pool_size的值是多少?你有多少内存?这可能是另一个问题。 -
@RickJames 请查看更新后的问题。 innodb_buffer_pool_size = 134217728;内存 = 8GB
-
没有好的方法可以使没有
WHERE子句的SELECT *更快。数据库必须对两个表进行全表扫描,因为您请求了 all 记录和 all 列。使查询速度更快的潜力在于使其更具体。 -
感谢您的意见。我的痛点实际上是更新 SQL。我刚刚在这里指定了 Select 等效项以使其变得简单。现在更改我的问题以显示实际的更新 SQL。
标签: performance mariadb sql-execution-plan