如何使这个 mysqli 查询在 PHP 中运行得更快


How can i make this mysqli query run faster in PHP?

$networks 是具有多个值的字符串,用逗号分隔。例:

$networks = "Programming,Movies,Hollywood". (There can be around 150 values or more.)    

现在Mysql查询在这里:

$query = "SELECT * FROM table 
          WHERE ( isActive = 1 AND 
                  isDeleted = 0 AND 
                  onid = '0' AND 
                  question = 0 AND 
                  ( ".$networkqur." )
                ) 
ORDER BY id DESC
LIMIT 0,100;

这里$networkqur是:

$network = explode(',',$networks);
$networkqur = '';
for( $i = 0; $i < count($network); $i++ ){
    $networkqur .= 'networks LIKE "%'.$network[$i].'%"';
    if( $i != count($network) - 1 ){
        $networkqur .= ' OR ';
    }
}

如此有效地$networkqur变成:

$networkqur = "networks LIKE "%Programming%" OR 
               networks LIKE "%Movies%" OR 
               networks LIKE "%Hollywood%";

有效查询变为:

$query = "SELECT * FROM posts
          WHERE ( isActive = 1 AND 
                  isDeleted = 0 AND 
                  onid = '0' AND 
                  question = 0 AND 
                   ( networks LIKE "%Programming%" OR 
                     networks LIKE "%Movies%" OR 
                     networks LIKE "%Hollywood% ) 
                   ) 
          ORDER BY id DESC
          LIMIT 0,100;

现在,正如我们所看到的,查询中可以有 150 个 OR 条件,最后可以有多个带有排序的 AND 条件。
是否可以替换此特定查询或任何其他更快的执行方式?

你在设计或数据库中犯了一个可怕的错误。 在设计数据库时应遵循六条数据库规范化规则,并且您已经打破了第一个也是最重要的规则 - 在每列中存储一条且仅一条信息。

除了在数据库之上实现复杂的全文索引系统之外,没有办法优化当前的设计。 此外,无法执行关系完整性(检查是否仅存储允许的network值(。 不能为这些值编制索引,也不能在 JOIN 中使用它们。 此外,您有一个嵌入式字符串问题,其中搜索(例如("Holly"将与"Holly","Hollywood"和"Holly Hunter"匹配。

相反,您应该将该networks列分解为单独的表名,post_networks具有列post_idnetwork列。 为每个帖子和网络组合添加一行,在(post_id, network)上添加一个主键,可能在(network, post_id)上添加一个主键,您将能够更快,更安全地进行此查询(以及更多(。

如果您的术语列表相对固定(即不是用户生成的(,那么这里的一个解决方案是构建您自己的索引表,然后对其进行检查。如果您仅在添加/编辑主要数据时才进行构建索引的接触点,这可以大大提高SELECT语句的速度。因此,您的索引表将具有每条记录的主键(理想情况下是PRIMARY KEY(,然后是对您要查找的内容的引用。然后,您可以将INDEX添加到术语列,您的速度应该会显着提高,因为您正在对索引列进行查找。

理想情况下,切勿对未编制索引的数据进行查找。