mysql - 如何重写 MySQL 查询

标签 mysql performance

我有以下查询,我正在尝试重写它以提高性能,我可以使用什么方法来重写它。

select 
    notes.id, notes.name, notes.parent_type, notes.contact_id from notes 
JOIN 
    ( 
    SELECT contact_id as id from accounts_contacts where account_id = 'acct1876' and deleted = '0' union 
    SELECT quote_id as id from quotes_accounts where account_id = 'acct1876' and deleted = '0' union 
    SELECT opportunity_id as id from accounts_opportunities where account_id = 'acct1876' and deleted = '0' union 
    SELECT leads.id as id from leads where account_id = 'acct1876' and deleted = '0' union 
    SELECT  project_id as id from projects_accounts where account_id = 'acct1876' and deleted = '0' union 
    select 'acct1876' as id 
    ) A 
    ON A.id = notes.parent_id and deleted = '0' OR contact_id in 
    ( SELECT contact_id from accounts_contacts where account_id = 'acct1876' and deleted = '0' ) and deleted = '0' 

    group by notes.id;

最佳答案

首先,您的最终 OR 与内部联接的开头重复,否则毫无意义。

这部分

  ON A.id = notes.parent_id 
  and deleted = '0' 
  OR contact_id in ( SELECT contact_id 
                       from accounts_contacts 
                       where account_id = 'acct1876' 
                       and deleted = '0' ) 
  and deleted = '0' 

可以只是

  ON A.id = notes.parent_id 

接下来,您似乎正在尝试获取与给定帐户关联的所有 ID,包括相关帐户。我会确保每个表在帐户 ID 和已删除列上都有一个索引。另外,对于这个查询,我将其设置为 DISTINCT 以防止将重复项连接到注释表中。然后我会交换顺序(对我来说,在心里查询你想要的 ID,然后获取关联的注释)。下面是 UNION 查询的每个表的覆盖索引,以及连接的父 ID 列的注释表。

table                  index
accounts_contacts      (account_id, deleted, contact_id)
quotes_accounts        (account_id, deleted, quote_id )
accounts_opportunities (account_id, deleted, opportunity_id )
leads                  (account_id, deleted, id
projects_accounts      (account_id, deleted, project_id )
notes                  (parent_id)

现在,小幅更新的查询

select 
      notes.id, 
      notes.name, 
      notes.parent_type, 
      notes.contact_id 
   from 
         (SELECT DISTINCT contact_id as id 
             from accounts_contacts 
             where account_id = 'acct1876' and deleted = '0' 
          union 
          SELECT quote_id as id 
             from quotes_accounts 
             where account_id = 'acct1876' and deleted = '0' 
          union 
          SELECT opportunity_id as id 
             from accounts_opportunities 
             where account_id = 'acct1876' and deleted = '0' 
          union 
          SELECT leads.id as id 
             from leads 
             where account_id = 'acct1876' and deleted = '0' 
          union 
          SELECT project_id as id 
             from projects_accounts 
             where account_id = 'acct1876' and deleted = '0' 
          union 
          select 'acct1876' as id ) A 
         JOIN Notes
            ON A.id = notes.parent_id 
   group by 
     notes.id;

正如有人指出的,您有一个分组依据,但列上没有求和或聚合,这将导致找到第一个包含此类的条目,并且由于出现自动递增 ID 列,因此将具有无论帐户“ID”来自何处,值都相同。

关于mysql - 如何重写 MySQL 查询,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21702980/

相关文章:

php - 查询计数和功能无法正常工作

c# - EF 多个不同版本的数据库

Mysql - 用 null 简化查询 EXIST

mysql查询所有子账户及其子账户等

javascript - 计算JavaScript中句子(数组)中字符(数组)的出现次数

C# mysql 使用 Byte[] 将文件插入数据库

c++ - 使用 valgrind 测量缓存未命中

mysql - 什么数据库可以很好地处理 200+GB 的数据?

performance - Asp.net Mvc 2 DisplayFor 性能问题?

mysql - 如何加速 MySQL INSERTs/UPDATEs?