我有一个查询
$query = "SELECT DISTINCT report_date,weekreportDate FROM contract_sales a
INNER JOIN contract b ON a.contract_UUID = b.UUID
INNER JOIN geoPoint c ON b.customer_UUID = c.customerUUID
WHERE c.com_UUID = '$com' AND a.report_date >= Date('$dateafter')
AND c.city_UUID = '$cit' ORDER BY `report_date`";
我需要做的是首先通过日期过滤去除所有结果,但是你可以看到我得到了所有内容,然后在支票中进行日期排序..
我内心加入所有人 - 有更好的方法吗?
我有一份关于每个日期的报告 - 并且有两年的数据 - 我想在2014年只获得日期,因为你可以看到我有700多个日期对我来说毫无用处但是我必须经历所有日期他们可以检查另一个字符串UUID ...我该怎么做才能加快我的工作(尽管工作速度慢)?
按要求解释信息:
Generation Time: Feb 20, 2014 at 06:48 PM
Generated by: phpMyAdmin 3.3.10.4 / MySQL 5.1.53-log
SQL query: EXPLAIN SELECT DISTINCT report_date,weekreportDate FROM contract_sales a INNER JOIN contract b ON a.contract_UUID = '1234' INNER JOIN geoPoint c ON b.customer_UUID = '1234' WHERE c.com_UUID = '1234' AND a.report_date >= Date('2014-01-01') AND c.city_UUID = '1234' ORDER BY `report_date`;
Rows: 3
id select_type table type possible_keys key key_len ref rows Extra
1 SIMPLE a ref uuid_conlcs uuid_conlcs 110 const 1 Using where; Using temporary; Using filesort
1 SIMPLE b ref uuid_cust uuid_cust 110 const 1 Using where; Using index; Distinct
1 SIMPLE c ref uuid_gargp,uuid_citgp uuid_citgp 110 const 1 Using where; Distinct
答案 0 :(得分:1)
首先,重写您的查询。我建议不要使用别名a,b,c,而是更接近于合约表的“cs”上下文,合同的“con”和geoPoint的“gp”......在更大的更复杂的查询中尤其容易。 / p>
此外,总是尝试使用table.column(或alias.column)限定查询,因为WeekReportDate不清楚,但它似乎与您的合同销售表关联。
对于这个构造中的索引,我会有一个索引(report_date,weekreportDate,contract_uuid)。这样,它就是一个覆盖索引,用于处理要检索的列,where子句,order by和join表,无需返回到原始数据页。
合约表,我有一个(UUID,customer_UUID)索引,也是合约销售加入的覆盖索引,也支持加入geoPoint表。
最后,您的geoPoint表,(customerUUID,com_uuid,city_uuid)上的索引也涵盖了联接和过滤条件。
SELECT DISTINCT
cs.report_date,
cs.weekreportDate
FROM
contract_sales cs
INNER JOIN contract con
ON cs.contract_UUID = con.UUID
INNER JOIN geoPoint gp
ON con.customer_UUID = gp.customerUUID
AND gp.com_UUID = '$com'
AND gp.city_UUID = '$cit'
WHERE
cs.report_date >= Date('$dateafter')
ORDER BY
cs.report_date
现在说了,而且我不知道你的表的构成量,但如果你正在寻找特定COM / City的东西,我会怀疑那些合格的记录会比有关日期范围的所有COM /城市。所以,我会反驳下面的查询,希望较小的数据集可以更快地查询,但你必须显然尝试两种方法。
SELECT DISTINCT
cs.report_date,
cs.weekreportDate
FROM
geoPoint gp
INNER JOIN contract con
ON gp.customerUUID = con.customer_UUID
JOIN contract_sales cs
ON con.UUID = cs.contract_UUID
AND cs.report_date >= Date('$dateafter')
WHERE
gp.com_UUID = '$com'
AND gp.city_UUID = '$cit'
ORDER BY
cs.report_date
实际上,geoPoint索引应首先在您的WHERE标准上,然后是连接到下一个表的客户UUID(com_uuid,city_uuid,customeruuid)。 (contract_UID,report_date)上的contract_sales索引和(customer_UUID,UUID)上的合同表索引,以匹配此查询的连接流。