Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/mysql/62.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
MySQL:优化不存在子查询的查询_Mysql_Sql - Fatal编程技术网

MySQL:优化不存在子查询的查询

MySQL:优化不存在子查询的查询,mysql,sql,Mysql,Sql,首先,我要说的是,我不是mySQL的大师;虽然我充分使用了它,但我不知道它的很多细节。在我刚刚继承的系统中,我得到了以下查询: SELECT DISTINCT profile2.f3 FROM node AS profile JOIN node AS profile2 ON ( profile.f1 = profile2.f1 ) WHERE profile.f2 = "aString" AND profile.f3 = "anotherStr

首先,我要说的是,我不是mySQL的大师;虽然我充分使用了它,但我不知道它的很多细节。在我刚刚继承的系统中,我得到了以下查询:

SELECT DISTINCT profile2.f3
FROM   node AS profile
       JOIN node AS profile2
         ON ( profile.f1 = profile2.f1 )
WHERE  profile.f2 = "aString"
       AND profile.f3 = "anotherString"
       AND profile2.f2 = "aThirdString"
       AND NOT EXISTS (SELECT profile3.f1
                       FROM   node AS profile3
                       WHERE  profile3.f1 = profile.f1
                              AND profile3.f2 = "yetAnotherString") ;
显示创建表
给出:

CREATE TABLE `node` (
  `id` bigint(20) NOT NULL AUTO_INCREMENT,
  `graph` varchar(100) CHARACTER SET latin1 DEFAULT NULL,
  `f1` varchar(200) NOT NULL,
  `f2` varchar(200) NOT NULL,
  `f3` mediumtext NOT NULL,
  PRIMARY KEY (`id`),
  UNIQUE KEY `nodeindex` (`graph`(20),`f1`(100),`f2`(100),`f3`(100)),
  KEY `ix_node_f1` (`f1`),
  KEY `ix_node_graph` (`graph`),
  KEY `ix_node_f3` (`f3`(255)),
  KEY `ix_node_f2` (`f2`),
  KEY `node_po` (`f2`,`f3`(130)),
  KEY `node_so` (`f1`,`f3`(130)),
  KEY `node_sp` (`f1`,`f2`(130)),
  FULLTEXT KEY `node_search` (`f3`)
) ENGINE=MyISAM AUTO_INCREMENT=455854703 DEFAULT CHARSET=utf8
+----+--------------------+----------+------+--------------------------------------------------------------------------------------+---------+---------+-----------------------------------+-------+----------+------------------------------+
| id | select_type        | table    | type | possible_keys                                                                        | key     | key_len | ref                               | rows  | filtered | Extra                        |
+----+--------------------+----------+------+--------------------------------------------------------------------------------------+---------+---------+-----------------------------------+-------+----------+------------------------------+
|  1 | PRIMARY            | profile  | ref  | ix_node_f1,ix_node_f3,ix_node_f2,node_po,node_so,node_sp,node_search                 | node_po | 994     | const,const                       | 49084 |   100.00 | Using where; Using temporary |
|  1 | PRIMARY            | profile2 | ref  | ix_node_f1,ix_node_f2,node_po,node_so,node_sp                                        | node_sp | 994     | sumazi_prdf.profile.f1,const      |     1 |   100.00 | Using where                  |
|  2 | DEPENDENT SUBQUERY | profile3 | ref  | ix_node_f1,ix_node_f2,node_po,node_so,node_sp                                        | node_sp | 994     | sumazi_prdf.profile.f1,const      |     1 |   100.00 | Using where                  |
+----+--------------------+----------+------+--------------------------------------------------------------------------------------+---------+---------+-----------------------------------+-------+----------+------------------------------+
EXPLAIN EXTENDED
给出:

CREATE TABLE `node` (
  `id` bigint(20) NOT NULL AUTO_INCREMENT,
  `graph` varchar(100) CHARACTER SET latin1 DEFAULT NULL,
  `f1` varchar(200) NOT NULL,
  `f2` varchar(200) NOT NULL,
  `f3` mediumtext NOT NULL,
  PRIMARY KEY (`id`),
  UNIQUE KEY `nodeindex` (`graph`(20),`f1`(100),`f2`(100),`f3`(100)),
  KEY `ix_node_f1` (`f1`),
  KEY `ix_node_graph` (`graph`),
  KEY `ix_node_f3` (`f3`(255)),
  KEY `ix_node_f2` (`f2`),
  KEY `node_po` (`f2`,`f3`(130)),
  KEY `node_so` (`f1`,`f3`(130)),
  KEY `node_sp` (`f1`,`f2`(130)),
  FULLTEXT KEY `node_search` (`f3`)
) ENGINE=MyISAM AUTO_INCREMENT=455854703 DEFAULT CHARSET=utf8
+----+--------------------+----------+------+--------------------------------------------------------------------------------------+---------+---------+-----------------------------------+-------+----------+------------------------------+
| id | select_type        | table    | type | possible_keys                                                                        | key     | key_len | ref                               | rows  | filtered | Extra                        |
+----+--------------------+----------+------+--------------------------------------------------------------------------------------+---------+---------+-----------------------------------+-------+----------+------------------------------+
|  1 | PRIMARY            | profile  | ref  | ix_node_f1,ix_node_f3,ix_node_f2,node_po,node_so,node_sp,node_search                 | node_po | 994     | const,const                       | 49084 |   100.00 | Using where; Using temporary |
|  1 | PRIMARY            | profile2 | ref  | ix_node_f1,ix_node_f2,node_po,node_so,node_sp                                        | node_sp | 994     | sumazi_prdf.profile.f1,const      |     1 |   100.00 | Using where                  |
|  2 | DEPENDENT SUBQUERY | profile3 | ref  | ix_node_f1,ix_node_f2,node_po,node_so,node_sp                                        | node_sp | 994     | sumazi_prdf.profile.f1,const      |     1 |   100.00 | Using where                  |
+----+--------------------+----------+------+--------------------------------------------------------------------------------------+---------+---------+-----------------------------------+-------+----------+------------------------------+

正如我所说,我不是RDBMS的专家,但我的直觉表明,这个查询的性能可以大大提高。有什么建议吗?

你可以试试这个,速度应该会快一些,或者你可以加入

   SELECT DISTINCT profile2.f3
    FROM   node AS profile
           JOIN node AS profile2
             ON ( profile.f1 = profile2.f1 )
    WHERE  profile.f2 = "aString"
           AND profile.f3 = "anotherString"
           AND profile2.f2 = "aThirdString"
           AND PROFILE.F1 NOT IN (SELECT profile3.f1
                           FROM   node AS profile3
                           WHERE  profile3.f2 = "yetAnotherString") ;

左连接。。。其中NULL往往比MySQL中不存在的子句快;在其他RDBMS中,情况往往相反。尝试:

SELECT DISTINCT profile2.f3
FROM node AS profile
JOIN node AS profile2 ON profile.f1 = profile2.f1
LEFT JOIN node AS profile3 ON profile.f1 = profile3.f1 
                     AND profile3.f2 = "yetAnotherString"
WHERE  profile.f2 = "aString"
  AND profile.f3 = "anotherString"
  AND profile2.f2 = "aThirdString"
  AND profile3.f1 IS NULL

您想只选择
profile2.f3
列吗?另外,请添加
SHOW CREATE TABLE节点输出。查询的
解释
也会有帮助。自连接加反连接。让我猜猜:EAV模型?@wildplasser EAV模型:足够近了。很好的拾取,但我正在尝试对其进行一点清理。如果不清楚,我的意思是“不,我一点也不介意。)为什么这会更快?因为不在构造结果集中,排除值,但不存在,其工作方式类似于联接,然后排除。