[英]How to optimize slow MySQL query
我有以下MySQL查詢,它需要很長時間才能執行:
SELECT `market`.`name` AS `Markets`, count(*) * `clicks`.`cost` AS `Rev`
FROM `clicks`
INNER JOIN markets ON `clicks`.`market_id`= `markets`.`id`
WHERE clicks.created_date = `date1`
GROUP BY `markets`.`id`
ORDER BY `Rev` DESC
最初它非常慢,但后來我刪除了冗余日期功能。 仍然需要很長時間才能執行。 有什么解決方案嗎?
查詢說明:我從一個表和行數中選擇市場名稱乘以另一個表的成本。 市場ID在第一個表“點擊”中定義,我從“市場”表中獲取市場名稱。 我進一步按照他們的ID對市場進行分組,然后通過Rev降序排序
您的查詢是按功能濫用MySQL 部分組 。 您按市場進行分組,但有一個clicks.cost
列的clicks.cost
,它不包含在聚合中。 無論查詢速度有多快,您都會得到錯誤的結果。
您可以按如下方式修改查詢:
SELECT market.name AS Markets, subqry.Rev FROM (
SELECT market_id, SUM(cost) AS Rev
FROM clicks
WHERE created_date = 'some date'
GROUP BY market_id
) AS subqry
INNER JOIN markets ON subqry.market_id = markets.id
ORDER BY Rev DESC
確保結果正確后,請創建以下索引:
CREATE INDEX ix_clicks ON clicks (created_date, market_id, cost)
據推測,你打算:
SELECT m.name AS Markets, SUM(c.cost) AS `Rev`
FROM clicks c INNER JOIN
markets m
ON c.market_id = m.id
WHERE c.created_date = ?
GROUP BY m.name
ORDER BY Rev DESC;
這對性能沒有幫助。 但是, clicks(created_date, market_id, cost)
索引clicks(created_date, market_id, cost)
可能會為您提供所需的性能。
如果這不起作用,那么試試這個:
SELECT m.name AS Markets,
(SELECT SUM(c.cost)
FROM clicks c
WHERE c.market_id = m.id AND c.created_date = ?
) AS `Rev`
FROM markets m
ORDER BY Rev DESC;
這將刪除外部GROUP BY
,這可以獲得很大的性能提升。 為此,索引應略有不同, clicks(market_id, created_date, cost)
。
我知道這不是問題的直接答案,如果你願意,你可以向我投票(我理解人性,對另類思想家表現出仇恨)。
但是我要編寫另外正確的方法來做這樣的邏輯系統,我們每天都有大量的數據,而且我們必須在沒有性能問題的情況下制作摘要報告。
不幸的是,這是時間序列數據。
它會增長並且會損失您的性能損失。
對於短期添加索引可能會解決您的問題。
但從長遠來看 ,許多市場將出現,點擊量將達到每天約100萬 ,“索引解決方案” 並不是一個好的解決方案。
A)如果你做索引日期字段你會慢速插入。 因為它每次都會在后台執行索引更新程序。
B)如果您對分區表進行分區,那么在一段時間之后很難管理,因為擁有數百個分區是不好的,並且某些日常業務將為當前數據結構帶來非常“不舒服”的任務,這將導致重新思考表模式。
解決方案是重新思考你的邏輯:
clicks
表(表不應該有索引以快速插入)。 clicks_by_markets
, clicks_by_markets_yearly
, clicks_by_markets_weekly
, clicks_by_markets_daily
另一個解決方案(沒有Kafka):
clicks_raw
來放置請求數據而不進行處理。 clicks_raw
表並填充表格,如: clicks_by_markets
, clicks_by_markets_yearly
, clicks_by_markets_weekly
, clicks_by_markets_daily
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.