一次優化記錄

2021-09-28 21:23:05 字數 1585 閱讀 1095

備註:由於隱私 部分使用了偽**,偽sql

直接查十點查全部 select * from 『使用者優惠券表』 where 優惠券id in (select id from 優惠券表 where 限制=新使用者 and 90天內)  總時間40+秒

這裡用exlpain分析 優惠券id是有索引的,但是實際上沒有走索引。是因為資料量過大。mysql會認為全表掃瞄比走索引效率高,就放棄索引走了全表掃瞄。第一次優化主要從這方面入手

先查詢新人優惠券ids,並對ids進行分組,再到優惠券使用者表查資料

1:select id from 優惠券表 where 領取限制=新使用者 取ids

2:for(int i=1;;i++)

符合條件的結果list=baseres.stream.map().filter()..collect(collects.tolist)取userid的list

這裡的思路是減少每次查詢的資料量,希望可以命中索引。多次跑這塊**實際結果用70-100多秒不等。比第一次還要慢。事後分析結果如下:

優惠每個優惠券的分布是不均的。可能有的多有的少。所以迴圈過程中。如果此次的優惠券組數量較少則會走索引。若資料量較大,還是會全表掃瞄。甚至可能出現全表掃瞄多次的情況。所以時間會更長。 於是第二次優化希望去找穩定的索引。

第二次優化從執行時間上進行優化,既然sql執行太久 可以用延時來做。讓業務低峰期去跑慢sql。於是在凌晨5點執行任務。跑完sql後 丟到scheduledexecutorsercice裡延時5小時跑。偽**:

set.foreach(o->

},5, timeunit.hours);

});這樣做基本可以避免業務對高峰期線上環境的影響。凌晨去跑乙個幾十秒的sql也是可以接受的方案。但是總感覺還有不少可以優化的空間。思考一晚後,第二天有了第三次優化。

因為業務只需要查進90天的優惠券。而資料庫的主鍵是自增的。所以可以通過主鍵來確定範圍。

1:select min(id) from 優惠券使用者表 where 時間》dateadd(currdate,interval -90 day) 得到minid

2: select id from 優惠券表 where 領取限制=新使用者 取ids

3:select * from '使用者優惠券表' where id >minid and 優惠券id in (ids)

explain 分析:

possible_keys:主鍵id,優惠券id

key:主鍵id

這裡顯示可能會走的索引用到了主鍵id,以及優惠券id兩個。但是實際用到的索引是主鍵索引。說明走優惠券id索引的話 。資料量過大。不如走全表掃瞄 返回資料100w左右。查詢時間45ms。資料傳輸時間5秒+。

1:對第三次結果還算滿意,本地執行的時候把五小時調成了5秒鐘。發現定時任務到執行時間時。控制台連續列印sql。發現

set.foreach(o->

},5, timeunit.hours);

});中 把使用者查詢也放到了執行緒池裡。導致在十點時,資料庫訪問量也會很大。就把使用者查詢提到了執行緒池外,凌晨去執行 如下:

set.foreach(o->

},5, timeunit.hours);

});這樣的話,十點執行的任務就只有乙個訊息推送了。

一次優化記錄

今天收到乙個同事的求助,說有乙個sql跑了乙個多小時沒有結果。我看了看,這個sql是這樣的 隱藏了敏感資訊 select 號碼,列2,列3,max starttime flag from 表1 t1 where flag 0 and 號碼 not in select 號碼 from 表2 t2 gr...

一次優化經歷

問題 excel資料匯入,儲存到資料庫中,為了優化查詢效率和其他一些業務需求,需要將資料的一列屬性切分後儲存到redis中,插入資料庫前要保證其中乙個屬性不重複,另外乙個屬性已經在資料庫中。為了將問題描述簡單些,我們假設excel中有兩列資料a和b,其中資料a要保證資料庫中不重複,資料b保證資料庫中...

一次優化web專案的經歷記錄(二)

前言 最近很長一段時間沒有更新部落格了,忙於一堆子專案的開發,嚴重拖慢了學習與思考的程序。開水倒滿了需要提早放下杯子,晚了就會燙手,這段時間以來,寫的東西越來越不嚴謹,各種低階錯誤頻出,早該停下總結並鞏固一下了。但出於一些原因一直沒付諸於行,終於,燙到手了 在python裡,這很容易實現,借助裝飾器...