您好,登錄后才能下訂單哦!
MySQL在大數據、高并發場景下的SQL語句優化和實踐是怎樣的,很多新手對此不是很清楚,為了幫助大家解決這個難題,下面小編將為大家詳細講解,有這方面需求的人可以來學習下,希望你能有所收獲。
主要針對中小型應用或網站,重點探討日常程序開發中SQL語句的優化問題,所謂“大數據”、“高并發”僅針對中小型應用而言,專業的數據庫運維大神請無視。以下實踐為個人在實際開發工作中,針對相對“大數據”和相對“高并發”場景的一些應對策略,部分措施并沒有經過嚴格的對比測試和原理分析。
減少查詢的影響結果集,避免出現全表掃描。
影響結果集是SQL優化的核心。影響結果集不是查詢返回的記錄數,而是查詢所掃描的結果數。通過Explain或Desc分析SQL,rows列的值即為影響結果集(還可以通過慢查詢日志的Rows_examined后面的數字得到)。
以下是我常用的一些SQL優化策略:
去掉不必要的查詢和搜索。其實在項目的實際應用中,很多查詢條件是可有可無的,能從源頭上避免的多余功能盡量砍掉,這是最簡單粗暴的解決方案。
合理使用索引和復合索引。建索引是SQL優化中最有效的手段。查找、刪除、更新以及排序時常用的字段可以適當建立索引。不過要注意,單條查詢不能同時使用多個索引,只能使用一個索引。查詢條件較多時,可以使用多個字段合并的復合索引。切記,使用復合索引時,查詢條件的字段順序需要與復合索引的字段順序保持一致。
謹慎使用notin等可能無法使用索引的條件。索引也不是什么時候都可以發揮作用的,當出現"notin","!=","like'%xx%'","isnull"等條件時,索引是無效的。使用這些條件的時候,請放到能有效使用索引的條件的右邊。設計表結構時,個人建議盡可能用int類型代替varchar類型,int類型部分時候可以通過大于或小于代替"!="等條件,同時也方便滿足一些需要按類型排序的需求,至于可讀性的問題,完善好數據庫設計文檔才是明智的選擇。同時建議把所有可能的字段設置為"notnull",并設置默認值,避免在where字句中出現"isnull"的判斷。
不要在where子句中的“=”左邊進行函數、算術運算或其他表達式運算,否則系統將無法正確使用索引。盡可能少用MySQL的函數,類似Now()完全可以通過程序實現并賦值,部分函數也可以通過適當的建立冗余字段來間接替代。
在where條件中使用or,可能導致索引無效。可用"unionall"或者"union"(會過濾重復數據,效率比前者低)代替,或程序上直接分開兩次獲取數據再合并,確保索引的有效利用。
不使用select*,倒不是能提高查詢效率,主要是減少輸出的數據量,提高傳輸速度。
避免類型轉換,這里所說的“類型轉換”是指where子句中出現字段的類型和傳入的參數類型不一致的時候發生的類型轉換。
分頁查詢的優化。頁數比較多的情況下,如limit10000,10影響的結果集是10010行,查詢速度會比較慢。推薦的解決方案是:先只查詢主鍵selectidfromtablewhere..orderby..limit10000,10(搜索條件和排序請建立索引),再通過主鍵去獲取數據。
統計相關的查詢。影響結果集往往巨大,且部分SQL語句本身已經難以優化。因此,應避免在業務高峰期執行統計相關的查詢,或者僅在從庫中執行統計查詢。部分統計數據,可以通過冗余的數據結構保存,同時建議把數據先保存在內存、緩存中(如redis),再按一定策略寫入數據庫。
不使用任何連表查詢,通過分庫和分表實現負載均衡。
看完上述內容是否對您有幫助呢?如果還想對相關知識有進一步的了解或閱讀更多相關文章,請關注億速云行業資訊頻道,感謝您對億速云的支持。
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。