Php 使用LIKE子句加速MySQL内部连接

Php 使用LIKE子句加速MySQL内部连接,php,mysql,sql,sql-update,inner-join,Php,Mysql,Sql,Sql Update,Inner Join,我有以下两个表,api_analytics_data和telecordia CREATE TABLE `api_analytics_data` ( `id` bigint(20) NOT NULL AUTO_INCREMENT, `upload_file_id` bigint(20) NOT NULL, `partNumber` varchar(100) DEFAULT NULL, `clei` varchar(45) DEFAULT NULL, `description`

我有以下两个表,api_analytics_data和telecordia

CREATE TABLE `api_analytics_data` (
  `id` bigint(20) NOT NULL AUTO_INCREMENT,
  `upload_file_id` bigint(20) NOT NULL,
  `partNumber` varchar(100) DEFAULT NULL,
  `clei` varchar(45) DEFAULT NULL,
  `description` varchar(150) DEFAULT NULL,
  `processed` tinyint(1) DEFAULT '0',
  PRIMARY KEY (`id`),
  KEY `idx_aad_clei` (`clei`),
  KEY `idx_aad_pn` (`partNumber`),
  KEY `id_aad_processed` (`processed`),
  KEY `idx_combo1` (`partNumber`,`clei`,`upload_file_id`)
) ENGINE=InnoDB CHARSET=latin1;

CREATE TABLE `telecordia` (
  `tid` int(11) NOT NULL AUTO_INCREMENT,
  `ProdID` varchar(50) DEFAULT NULL,
  `Mfg` varchar(20) DEFAULT NULL,
  `Pn` varchar(50) DEFAULT NULL,
  `Clei` varchar(50) DEFAULT NULL,
  `Series` varchar(50) DEFAULT NULL,
  `Dsc` varchar(50) DEFAULT NULL,
  `Eci` varchar(50) DEFAULT NULL,
  `AddDate` date DEFAULT NULL,
  `ChangeDate` date DEFAULT NULL,
  `Cost` float DEFAULT NULL,
  PRIMARY KEY (`tid`),
  KEY `telecordia.ProdID` (`ProdID`) USING BTREE,
  KEY `telecordia.clei` (`Clei`),
  KEY `telecordia.pn` (`Pn`),
  KEY `telcordia.eci` (`Eci`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
用户使用Excel/CSV文件通过web界面将数据上传到api_analytics_数据中。数据包含零件号或CLEI。然后,我通过加入telecordia表来更新api_analytics_数据表。telecordia表是零件号和Cleis的主列表

因此,如果用户上载CLEIs文件,我使用的更新/加入是:

update api_analytics_data aad
  inner join telecordia t on aad.clei = t.Clei
  set aad.partNumber = t.Pn
  where aad.partNumber is null
  and aad.upload_file_id = 5;
它工作得很快,但不是很彻底。我的问题是上传的CLEI可能只是telecordia表中CLEI的一个子串

例如,上传的CLEI可以是“5SC1DX0”。在telcordia表中,正确的匹配行是:

tid:        184324    
ProdID:     472467  
Mfg:        PLSE 
Pn:         AUA58-2-REV-E            
Clei:       5SC1DX04AA        
Series:     null
Dsc:        DL SGL-PTY POTS CU RT                
Eci:        205756    
AddDate:    1994-03-18      
ChangeDate: 1998-04-13     
Cost:       null
所以很明显,我的更新在这种情况下不起作用,即使5SC1DX05SC1DX04AA是同一部分

我需要的是通配符搜索。然而,当我尝试这个,它是疯狂的缓慢。当大约4500行上传到api_analytics_数据表时,它会运行大约10分钟,然后失去与服务器的连接

update api_analytics_data aad
  inner join telecordia t on aad.clei like concat(t.Clei,'%')
  set aad.partNumber = t.Pn
  where aad.partNumber is null 
  and aad.upload_file_id = 5;
有没有一种方法可以优化它以使其快速运行

正确答案是“不”。更好的做法是在
telecordia
中创建一个新列,其中包含正确的
Clei
值,该值可用于连接表。在MySQL的最新版本中,它甚至可以是一个计算列并被索引

也就是说,如果匹配的部分总是相同的长度,那么您可能能够做一些事情。如果是,请尝试以下方法:

update api_analytics_data aad inner join
       telecordia t
       on t.Clei = left(aad.clei, 7)
  set aad.partNumber = t.Pn
  where aad.partNumber is null and aad.upload_file_id = 5;
对于此查询,您需要一个关于
api\u analytics\u数据(上传文件id、零件号、clei)
telecordia(clei、pn)
的索引。正确答案是“否”。更好的做法是在
telecordia
中创建一个新列,其中包含正确的
Clei
值,该值可用于连接表。在MySQL的最新版本中,它甚至可以是一个计算列并被索引

也就是说,如果匹配的部分总是相同的长度,那么您可能能够做一些事情。如果是,请尝试以下方法:

update api_analytics_data aad inner join
       telecordia t
       on t.Clei = left(aad.clei, 7)
  set aad.partNumber = t.Pn
  where aad.partNumber is null and aad.upload_file_id = 5;

对于这个查询,您需要在
api\u analytics\u数据(upload\u fiel\u id,partNumber,clei)
telecordia(clei,pn)

上建立索引:aad.clei,t.clei,aad.partNumber,aad.upload\u文件如果您使用的是MySQL 5.6及以上版本,您可以在创建表/列时使用为表/列启用的全文搜索功能,也可以更改表以启用它。您可以找到有关它的更多详细信息
idx_aad_pn
-此索引是冗余的。请确保以下索引具有索引:aad.clei、t.clei、aad.partNumber、aad.upload_file_idi如果您使用的是MySQL 5.6及更高版本,您可以在创建表/列时使用已启用的全文搜索功能,或者更改表以启用它。您可以找到有关它的更多详细信息
idx\u aad\u pn
-此索引是冗余的不幸的是,没有“正确”的CLEI。这些零件标识符都是不同长度的,由不同的代码组成。因此,对于CLEI'SP3QAF0BAA',SP是家族代码,3Q是子家族代码,AF0是特征代码,B是参考代码,AA是补充代码。所以SP3QA、SP3QAF、SP3QAF0、SP3QAF0B等都是同一部分。@scott80109。听起来你需要一个参考表给我。不幸的是,没有“正确”的CLEI。这些零件标识符都是不同长度的,由不同的代码组成。因此,对于CLEI'SP3QAF0BAA',SP是家族代码,3Q是子家族代码,AF0是特征代码,B是参考代码,AA是补充代码。所以SP3QA、SP3QAF、SP3QAF0、SP3QAF0B等都是同一部分。@scott80109。听起来你需要给我一张参考表。