實踐中應該如何優(yōu)化MySQL

本文主要給大家介紹實踐中應該如何優(yōu)化MySQL,其所涉及的東西,從理論知識來獲悉,有很多書籍、文獻可供大家參考,從現(xiàn)實意義來講,創(chuàng)新互聯(lián)累計多年的實踐經驗可分享給大家。

創(chuàng)新互聯(lián)公司一直秉承“誠信做人,踏實做事”的原則,不欺瞞客戶,是我們最起碼的底線! 以服務為基礎,以質量求生存,以技術求發(fā)展,成交一個客戶多一個朋友!為您提供成都網(wǎng)站設計、成都網(wǎng)站建設、外貿網(wǎng)站建設、成都網(wǎng)頁設計、小程序開發(fā)、成都網(wǎng)站開發(fā)、成都網(wǎng)站制作、成都軟件開發(fā)、APP應用開發(fā)是成都本地專業(yè)的網(wǎng)站建設和網(wǎng)站設計公司,等你一起來見證!

實踐中如何優(yōu)化MySQL

實踐中,MySQL的優(yōu)化主要涉及SQL語句及索引的優(yōu)化、數(shù)據(jù)表結構的優(yōu)化、系統(tǒng)配置的優(yōu)化和硬件的優(yōu)化四個方面,如下圖所示:

實踐中應該如何優(yōu)化MySQL

SQL語句及索引的優(yōu)化

SQL語句的優(yōu)化

SQL語句的優(yōu)化主要包括三個問題,即如何發(fā)現(xiàn)有問題的SQL、如何分析SQL的執(zhí)行計劃以及如何優(yōu)化SQL,下面將逐一解釋。

  1. 怎么發(fā)現(xiàn)有問題的SQL?(通過MySQL慢查詢日志對有效率問題的SQL進行監(jiān)控)

MySQL的慢查詢日志是MySQL提供的一種日志記錄,它用來記錄在MySQL中響應時間超過閥值的語句,具體指運行時間超過long_query_time值的SQL,則會被記錄到慢查詢日志中。

實踐中應該如何優(yōu)化MySQL

long_query_time的默認值為10,意思是運行10s以上的語句。慢查詢日志的相關參數(shù)如下所示:

實踐中應該如何優(yōu)化MySQL

通過MySQL的慢查詢日志,我們可以查詢出執(zhí)行的次數(shù)多占用的時間長的SQL、可以通過pt_query_disgest(一種mysql慢日志分析工具)分析Rows examine(MySQL執(zhí)行器需要檢查的行數(shù))項去找出IO大的SQL以及發(fā)現(xiàn)未命中索引的SQL,對于這些SQL,都是我們優(yōu)化的對象。

通過explain查詢和分析SQL的執(zhí)行計劃

使用 EXPLAIN 關鍵字可以知道MySQL是如何處理你的SQL語句的,以便分析查詢語句或是表結構的性能瓶頸。通過explain命令可以得到表的讀取順序、數(shù)據(jù)讀取操作的操作類型、哪些索引可以使用、哪些索引被實際使用、表之間的引用以及每張表有多少行被優(yōu)化器查詢等問題。當擴展列extra出現(xiàn)Using filesort和Using temporay,則往往表示SQL需要優(yōu)化了。

優(yōu)化SQL語句

  • 優(yōu)化insert語句:一次插入多值;

  • 應盡量避免在 where 子句中使用!=或<>操作符,否則將引擎放棄使用索引而進行全表掃描;

  • 應盡量避免在 where 子句中對字段進行null值判斷,否則將導致引擎放棄使用索引而進行全表掃描;

  • 優(yōu)化嵌套查詢:子查詢可以被更有效率的連接(Join)替代;

  • 很多時候用 exists 代替 in 是一個好的選擇。

索引優(yōu)化

建議在經常作查詢選擇的字段、經常作表連接的字段以及經常出現(xiàn)在order by、group by、distinct 后面的字段中建立索引。但必須注意以下幾種可能會引起索引失效的情形:

  • 以“%(表示任意0個或多個字符)”開頭的LIKE語句,模糊匹配;

  • OR語句前后沒有同時使用索引;

  • 數(shù)據(jù)類型出現(xiàn)隱式轉化(如varchar不加單引號的話可能會自動轉換為int型);

  • 對于多列索引,必須滿足最左匹配原則(eg,多列索引col1、col2和col3,則 索引生效的情形包括col1或col1,col2或col1,col2,col3)。

數(shù)據(jù)庫表結構的優(yōu)化

數(shù)據(jù)庫表結構的優(yōu)化包括選擇合適數(shù)據(jù)類型、表的范式的優(yōu)化、表的垂直拆分和表的水平拆分等手段。

選擇合適數(shù)據(jù)類型
  • 使用較小的數(shù)據(jù)類型解決問題;

  • 使用簡單的數(shù)據(jù)類型(mysql處理int要比varchar容易);

  • 盡可能的使用not null 定義字段;

  • 盡量避免使用text類型,非用不可時最好考慮分表;

表的范式的優(yōu)化

一般情況下,表的設計應該遵循三大范式。

表的垂直拆分
  • 把含有多個列的表拆分成多個表,解決表寬度問題,具體包括以下幾種拆分手段:

  • 把不常用的字段單獨放在同一個表中;

  • 把大字段獨立放入一個表中;

  • 把經常使用的字段放在一起;

  • 這樣做的好處是非常明顯的,具體包括:拆分后業(yè)務清晰,拆分規(guī)則明確、系統(tǒng)之間整合或擴展容易、數(shù)據(jù)維護簡單。

表的水平拆分

表的水平拆分用于解決數(shù)據(jù)表中數(shù)據(jù)過大的問題,水平拆分每一個表的結構都是完全一致的。一般地,將數(shù)據(jù)平分到N張表中的常用方法包括以下兩種:

  • 對ID進行hash運算,如果要拆分成5個表,mod(id,5)取出0~4個值;

  • 針對不同的hashID將數(shù)據(jù)存入不同的表中;

  • 表的水平拆分會帶來一些問題和挑戰(zhàn),包括跨分區(qū)表的數(shù)據(jù)查詢、統(tǒng)計及后臺報表的操作等問題,但也帶來了一些切實的好處:

    • 表分割后可以降低在查詢時需要讀的數(shù)據(jù)和索引的頁數(shù),同時也降低了索引的層數(shù),提高查詢速度;

    • 表中的數(shù)據(jù)本來就有獨立性,例如表中分別記錄各個地區(qū)的數(shù)據(jù)或不同時期的數(shù)據(jù),特別是有些數(shù)據(jù)常用,而另外一些數(shù)據(jù)不常用。

  • 需要把數(shù)據(jù)存放到多個數(shù)據(jù)庫中,提高系統(tǒng)的總體可用性(分庫,雞蛋不能放在同一個籃子里)。

系統(tǒng)配置的優(yōu)化

操作系統(tǒng)配置的優(yōu)化:增加TCP支持的隊列數(shù)

mysql配置文件優(yōu)化:Innodb緩存池設置(innodb_buffer_pool_size,推薦總內存的75%)和緩存池的個數(shù)(innodb_buffer_pool_instances)

硬件的優(yōu)化

CPU:核心數(shù)多并且主頻高的 內存:增大內存 磁盤配置和選擇:磁盤性能

MySQL中的悲觀鎖與樂觀鎖的實現(xiàn)

悲觀鎖與樂觀鎖是兩種常見的資源并發(fā)鎖設計思路,也是并發(fā)編程中一個非?;A的概念。

悲觀鎖

悲觀鎖的特點是先獲取鎖,再進行業(yè)務操作,即“悲觀”的認為所有的操作均會導致并發(fā)安全問題,因此要先確保獲取鎖成功再進行業(yè)務操作。通常來講,在數(shù)據(jù)庫上的悲觀鎖需要數(shù)據(jù)庫本身提供支持,即通過常用的select … for update操作來實現(xiàn)悲觀鎖。當數(shù)據(jù)庫執(zhí)行select … for update時會獲取被select中的數(shù)據(jù)行的行鎖,因此其他并發(fā)執(zhí)行的select … for update如果試圖選中同一行則會發(fā)生排斥(需要等待行鎖被釋放),因此達到鎖的效果。select for update獲取的行鎖會在當前事務結束時自動釋放,因此必須在事務中使用。    這里需要特別注意的是,不同的數(shù)據(jù)庫對select… for update的實現(xiàn)和支持都是有所區(qū)別的,例如oracle支持select for update no wait,表示如果拿不到鎖立刻報錯,而不是等待,mysql就沒有no wait這個選項。另外,mysql還有個問題是: select… for update語句執(zhí)行中所有掃描過的行都會被鎖上,這一點很容易造成問題。因此,如果在mysql中用悲觀鎖務必要確定使用了索引,而不是全表掃描。

樂觀鎖

樂觀鎖的特點先進行業(yè)務操作,只在最后實際更新數(shù)據(jù)時進行檢查數(shù)據(jù)是否被更新過,若未被更新過,則更新成功;否則,失敗重試。樂觀鎖在數(shù)據(jù)庫上的實現(xiàn)完全是邏輯的,不需要數(shù)據(jù)庫提供特殊的支持。一般的做法是在需要鎖的數(shù)據(jù)上增加一個版本號或者時間戳,然后按照如下方式實現(xiàn):

SELECT data AS old_data, version AS old_version FROM …;
//根據(jù)獲取的數(shù)據(jù)進行業(yè)務操作,得到new_data和new_version
UPDATE SET data = new_data, version = new_version WHERE version = old_version
if (updated row > 0) {
// 樂觀鎖獲取成功,操作完成
} else {
// 樂觀鎖獲取失敗,回滾并重試
}

樂觀鎖是否在事務中其實都是無所謂的,其底層機制是這樣:在數(shù)據(jù)庫內部update同一行的時候是不允許并發(fā)的,即數(shù)據(jù)庫每次執(zhí)行一條update語句時會獲取被update行的寫鎖,直到這一行被成功更新后才釋放。因此在業(yè)務操作進行前獲取需要鎖的數(shù)據(jù)的當前版本號,然后實際更新數(shù)據(jù)時再次對比版本號確認與之前獲取的相同,并更新版本號,即可確認這其間沒有發(fā)生并發(fā)的修改。如果更新失敗,即可認為老版本的數(shù)據(jù)已經被并發(fā)修改掉而不存在了,此時認為獲取鎖失敗,需要回滾整個業(yè)務操作并可根據(jù)需要重試整個過程。

悲觀鎖與樂觀鎖的應用場景

一般情況下,讀多寫少更適合用樂觀鎖,讀少寫多更適合用悲觀鎖。樂觀鎖在不發(fā)生取鎖失敗的情況下開銷比悲觀鎖小,但是一旦發(fā)生失敗回滾開銷則比較大,因此適合用在取鎖失敗概率比較小的場景,可以提升系統(tǒng)并發(fā)性能。

MySQL存儲引擎中的MyISAM和InnoDB區(qū)別詳解

在MySQL 5.5之前,MyISAM是mysql的默認數(shù)據(jù)庫引擎,其由早期的ISAM(Indexed Sequential Access Method:有索引的順序訪問方法)所改良。雖然MyISAM性能極佳,但卻有一個顯著的缺點: 不支持事務處理。不過,MySQL也導入了另一種數(shù)據(jù)庫引擎InnoDB,以強化參考完整性與并發(fā)違規(guī)處理機制,后來就逐漸取代MyISAM。

InnoDB是MySQL的數(shù)據(jù)庫引擎之一,其由Innobase oy公司所開發(fā),2006年五月由甲骨文公司并購。與傳統(tǒng)的ISAM、MyISAM相比,InnoDB的最大特色就是支持ACID兼容的事務功能,類似于PostgreSQL。目前InnoDB采用雙軌制授權,一是GPL授權,另一是專有軟件授權。具體地,MyISAM與InnoDB作為MySQL的兩大存儲引擎的差異主要包括:

存儲結構:每個MyISAM在磁盤上存儲成三個文件:第一個文件的名字以表的名字開始,擴展名指出文件類型。.frm文件存儲表定義,數(shù)據(jù)文件的擴展名為.MYD (MYData),索引文件的擴展名是.MYI (MYIndex)。InnoDB所有的表都保存在同一個數(shù)據(jù)文件中(也可能是多個文件,或者是獨立的表空間文件),InnoDB表的大小只受限于操作系統(tǒng)文件的大小,一般為2GB。

存儲空間:MyISAM可被壓縮,占據(jù)的存儲空間較小,支持靜態(tài)表、動態(tài)表、壓縮表三種不同的存儲格式。InnoDB需要更多的內存和存儲,它會在主內存中建立其專用的緩沖池用于高速緩沖數(shù)據(jù)和索引。

可移植性、備份及恢復:MyISAM的數(shù)據(jù)是以文件的形式存儲,所以在跨平臺的數(shù)據(jù)轉移中會很方便,同時在備份和恢復時也可單獨針對某個表進行操作。InnoDB免費的方案可以是拷貝數(shù)據(jù)文件、備份 binlog,或者用 mysqldump,在數(shù)據(jù)量達到幾十G的時候就相對痛苦了。

事務支持:MyISAM強調的是性能,每次查詢具有原子性,其執(zhí)行數(shù)度比InnoDB類型更快,但是不提供事務支持。InnoDB提供事務、外鍵等高級數(shù)據(jù)庫功能,具有事務提交、回滾和崩潰修復能力。

AUTO_INCREMENT:在MyISAM中,可以和其他字段一起建立聯(lián)合索引。引擎的自動增長列必須是索引,如果是組合索引,自動增長可以不是第一列,它可以根據(jù)前面幾列進行排序后遞增。InnoDB中必須包含只有該字段的索引,并且引擎的自動增長列必須是索引,如果是組合索引也必須是組合索引的第一列。

表鎖差異:MyISAM只支持表級鎖,用戶在操作MyISAM表時,select、update、delete和insert語句都會給表自動加鎖,如果加鎖以后的表滿足insert并發(fā)的情況下,可以在表的尾部插入新的數(shù)據(jù)。InnoDB支持事務和行級鎖。行鎖大幅度提高了多用戶并發(fā)操作的新能,但是InnoDB的行鎖,只是在WHERE的主鍵是有效的,非主鍵的WHERE都會鎖全表的。

全文索引:MyISAM支持 FULLTEXT類型的全文索引;InnoDB不支持FULLTEXT類型的全文索引,但是innodb可以使用sphinx插件支持全文索引,并且效果更好。

表主鍵:MyISAM允許沒有任何索引和主鍵的表存在,索引都是保存行的地址。對于InnoDB,如果沒有設定主鍵或者非空唯一索引,就會自動生成一個6字節(jié)的主鍵(用戶不可見),數(shù)據(jù)是主索引的一部分,附加索引保存的是主索引的值。

表的具體行數(shù):MyISAM保存表的總行數(shù),select count() from table;會直接取出出該值;而InnoDB沒有保存表的總行數(shù),如果使用select count() from table;就會遍歷整個表,消耗相當大,但是在加了wehre條件后,myisam和innodb處理的方式都一樣。

CURD操作:在MyISAM中,如果執(zhí)行大量的SELECT,MyISAM是更好的選擇。對于InnoDB,如果你的數(shù)據(jù)執(zhí)行大量的INSERT或UPDATE,出于性能方面的考慮,應該使用InnoDB表。DELETE從性能上InnoDB更優(yōu),但DELETE FROM table時,InnoDB不會重新建立表,而是一行一行的刪除,在innodb上如果要清空保存有大量數(shù)據(jù)的表,最好使用truncate table這個命令。

外鍵:MyISAM不支持外鍵,而InnoDB支持外鍵。

通過上述的分析,基本上可以考慮使用InnoDB來替代MyISAM引擎了,原因是InnoDB自身很多良好的特點,比如事務支持、存儲過程、視圖、行級鎖、外鍵等等。尤其在并發(fā)很多的情況下,相信InnoDB的表現(xiàn)肯定要比MyISAM強很多。另外,必須需要注意的是,任何一種表都不是萬能的,合適的才是最好的,才能最大的發(fā)揮MySQL的性能優(yōu)勢。如果是不復雜的、非關鍵的Web應用,還是可以繼續(xù)考慮MyISAM的,這個具體情況具體考慮。

MyISAM:不支持事務,不支持外鍵,表鎖;插入數(shù)據(jù)時鎖定整個表,查行數(shù)時無需整表掃描。主索引數(shù)據(jù)文件和索引文件分離;與主索引無區(qū)別;

InnoDB:支持事務,外鍵,行鎖,查表總行數(shù)時,全表掃描;主索引的數(shù)據(jù)文件本身就是索引文件;輔助索引記錄主鍵的值;

MySQL鎖類型  

根據(jù)鎖的類型分,可以分為共享鎖,排他鎖,意向共享鎖和意向排他鎖。

根據(jù)鎖的粒度分,又可以分為行鎖,表鎖。

對于mysql而言,事務機制更多是靠底層的存儲引擎來實現(xiàn),因此,mysql層面只有表鎖,而支持事務的innodb存 儲引擎則實現(xiàn)了行鎖(記錄鎖(在行相應的索引記錄上的鎖)),gap鎖(是在索引記錄間歇上的鎖),next-key鎖(是記錄鎖和在此索引記錄之前的gap上的鎖的結合)。Mysql的記錄鎖實質是索引記錄的鎖,因為innodb是索引組織表;gap鎖是索引記錄間隙的鎖,這種鎖只在RR隔離級別下有效;next-key鎖是記錄鎖加上記錄之前gap鎖的組合。mysql通過gap鎖和next-key鎖實現(xiàn)RR隔離級別。

說明:對于更新操作(讀不上鎖),只有走索引才可能上行鎖;否則會對聚簇索引的每一行上寫鎖,實際等同于對表上寫鎖。    若多個物理記錄對應同一個索引,若同時訪問,也會出現(xiàn)鎖沖突;

當表有多個索引時,不同事務可以用不同的索引鎖住不同的行,另外innodb會同時用行鎖對數(shù)據(jù)記錄(聚簇索引)加鎖。

MVCC(多版本并發(fā)控制)并發(fā)控制機制下,任何操作都不會阻塞讀操作,讀操作也不會阻塞任何操作,只因為讀不上鎖。    共享鎖:由讀表操作加上的鎖,加鎖后其他用戶只能獲取該表或行的共享鎖,不能獲取排它鎖,也就是說只能讀不能寫

排它鎖:由寫表操作加上的鎖,加鎖后其他用戶不能獲取該表或行的任何鎖,典型是mysql事務中的更新操作。

意向共享鎖(IS):事務打算給數(shù)據(jù)行加行共享鎖,事務在給一個數(shù)據(jù)行加共享鎖前必須先取得該表的IS鎖。

意向排他鎖(IX):事務打算給數(shù)據(jù)行加行排他鎖,事務在給一個數(shù)據(jù)行加排他鎖前必須先取得該表的IX鎖。

數(shù)據(jù)庫死鎖概念

多數(shù)情況下,可以認為如果一個資源被鎖定,它總會在以后某個時間被釋放。而死鎖發(fā)生在當多個進程訪問同一數(shù)據(jù)庫時,其中每個進程擁有的鎖都是其他進程所需的,由此造成每個進程都無法繼續(xù)下去。簡單的說,進程A等待進程B釋放他的資源,B又等待A釋放他的資源,這樣就互相等待就形成死鎖。

雖然進程在運行過程中,可能發(fā)生死鎖,但死鎖的發(fā)生也必須具備一定的條件,死鎖的發(fā)生必須具備以下四個必要條件:

1)互斥條件:指進程對所分配到的資源進行排它性使用,即在一段時間內某資源只由一個進程占用。如果此時還有其它進程請求資源,則請求者只能等待,直至占有資源的進程用畢釋放。    2)請求和保持條件:指進程已經保持至少一個資源,但又提出了新的資源請求,而該資源已被其它進程占有,此時請求進程阻塞,但又對自己已獲得的其它資源保持不放。    3)不剝奪條件:指進程已獲得的資源,在未使用完之前,不能被剝奪,只能在使用完時由自己釋放。    4)環(huán)路等待條件:指在發(fā)生死鎖時,必然存在一個進程——資源的環(huán)形鏈,即進程集合{P0,P1,P2,???,Pn}中的P0正在等待一個P1占用的資源;P1正在等待P2占用的資源,……,Pn正在等待已被P0占用的資源。    下列方法有助于最大限度地降低死鎖:

  • 按同一順序訪問對象。

  • 避免事務中的用戶交互。

  • 保持事務簡短并在一個批處理中。

  • 使用低隔離級別。

  • 使用綁定連接。

千萬級MySQL數(shù)據(jù)庫建立索引的事項及提高性能的手段

  1. 對查詢進行優(yōu)化,應盡量避免全表掃描,首先應考慮在 where 及 order by 涉及的列上建立索引。

  2. 應盡量避免在 where 子句中對字段進行 null 值判斷,否則將導致引擎放棄使用索引而進行全表掃描,如:select id from t where num is null可以在num上設置默認值0,確保表中num列沒有null值,然后這樣查詢:select id from t where num=0

  3. 應盡量避免在 where 子句中使用!=或<>操作符,否則引擎將放棄使用索引而進行全表掃描。

  4. 應盡量避免在 where 子句中使用or 來連接條件,否則將導致引擎放棄使用索引而進行全表掃描,如:select id from t where num=10 or num=20可以這樣查詢:select id from t where num=10 union all select id from t where num=20

  5. in 和 not in 也要慎用,否則會導致全表掃描,如:select id from t where num in(1,2,3) 對于連續(xù)的數(shù)值,能用 between 就不要用 in 了:select id from t where num between 1 and 3

  6. 避免使用通配符。下面的查詢也將導致全表掃描:select id from t where name like ‘李%’若要提高效率,可以考慮全文檢索。

  7. 如果在 where 子句中使用參數(shù),也會導致全表掃描。因為SQL只有在運行時才會解析局部變量,但優(yōu)化程序不能將訪問計劃的選擇推遲到運行時;它必須在編譯時進行選擇。然而,如果在編譯時建立訪問計劃,變量的值還是未知的,因而無法作為索引選擇的輸入項。如下面語句將進行全表掃描:select id from t where num=@num可以改為強制查詢使用索引:select id from t with(index(索引名)) where num=@num

  8. 應盡量避免在 where 子句中對字段進行表達式操作,這將導致引擎放棄使用索引而進行全表掃描。如:select id from t where num/2=100應改為:select id from t where num=100*2

  9. 應盡量避免在where子句中對字段進行函數(shù)操作,這將導致引擎放棄使用索引而進行全表掃描。如:select id from t where substring(name,1,3)=’abc’ ,name以abc開頭的id應改為:select id from t where name like ‘abc%’

  10. 不要在 where 子句中的“=”左邊進行函數(shù)、算術運算或其他表達式運算,否則系統(tǒng)將可能無法正確使用索引。

  11. 在使用索引字段作為條件時,如果該索引是復合索引,那么必須使用到該索引中的第一個字段作為條件時才能保證系統(tǒng)使用該索引,否則該索引將不會被使用,并且應盡可能的讓字段順序與索引順序相一致。

  12. 不要寫一些沒有意義的查詢,如需要生成一個空表結構:select col1,col2 into #t from t where 1=0 這類代碼不會返回任何結果集,但是會消耗系統(tǒng)資源的,應改成這樣:create table #t(…)

  13. 很多時候用 exists 代替 in 是一個好的選擇:select num from a where num in(select num from b)用下面的語句替換:select num from a where exists(select 1 from b where num=a.num)

  14. 并不是所有索引對查詢都有效,SQL是根據(jù)表中數(shù)據(jù)來進行查詢優(yōu)化的,當索引列有大量數(shù)據(jù)重復時,SQL查詢可能不會去利用索引,如一表中有字段sex,male、female幾乎各一半,那么即使在sex上建了索引也對查詢效率起不了作用。

  15. 索引并不是越多越好,索引固然可以提高相應的 select 的效率,但同時也降低了insert 及 update 的 效率,因為 insert 或 update 時有可能會重建索引,所以怎樣建索引需要慎重考慮,視具體情況而定。一個表的索引數(shù)最好不要超過6個,若太多則應考慮一些不常使用到的列上建的索引是否有 必要。

  16. 應盡可能的避免更新 clustered 索引數(shù)據(jù)列,因為 clustered 索引數(shù)據(jù)列的順序就是表記錄的物理存儲 順序,一旦該列值改變將導致整個表記錄的順序的調整,會耗費相當大的資源。若應用系統(tǒng)需要頻繁更新 clustered 索引數(shù)據(jù)列,那么需要考慮是否應將該索引建為 clustered 索引。

  17. 盡量使用數(shù)字型字段,若只含數(shù)值信息的字段盡量不要設計為字符型,這會降低查詢和連接的性能,并會增加存儲開銷。這是因為引擎在處理查詢和連接時會逐個比較字符串中每一個字符,而對于數(shù)字型而言只需要比較一次就夠了。

  18. 盡可能的使用 varchar/nvarchar 代替 char/nchar ,因為首先變長字段存儲空間小,可以節(jié)省存儲空間,其次對于查詢來說,在一個相對較小的字段內搜索效率顯然要高些。

  19. 任何地方都不要使用 select * from t ,用具體的字段列表代替“*”,不要返回用不到的任何字段。

  20. 盡量使用表變量來代替臨時表。如果表變量包含大量數(shù)據(jù),請注意索引非常有限(只有主鍵索引)。

  21. 避免頻繁創(chuàng)建和刪除臨時表,以減少系統(tǒng)表資源的消耗。

  22. 臨時表并不是不可使用,適當?shù)厥褂盟鼈兛梢允鼓承├谈行?,例如,當需要重復引用大型表或常用表中的某個數(shù)據(jù)集時。但是,對于一次性事件,最好使用導出表。

  23. 在新建臨時表時,如果一次性插入數(shù)據(jù)量很大,那么可以使用 select into 代替 create table,避免造成大量 log ,以提高速度;如果數(shù)據(jù)量不大,為了緩和系統(tǒng)表的資源,應先create table,然后insert。

  24. 如果使用到了臨時表,在存儲過程的最后務必將所有的臨時表顯式刪除,先 truncate table ,然后 drop table ,這樣可以避免系統(tǒng)表的較長時間鎖定。

  25. 盡量避免使用游標,因為游標的效率較差,如果游標操作的數(shù)據(jù)超過1萬行,那么就應該考慮改寫。

  26. 使用基于游標的方法或臨時表方法之前,應先尋找基于集的解決方案來解決問題,基于集的方法通常更有效。

  27. 與臨時表一樣,游標并不是不可使用。對小型數(shù)據(jù)集使用 FAST_FORWARD 游標通常要優(yōu)于其他逐行處理方法,尤其是在必須引用幾個表才能獲得所需的數(shù)據(jù)時。在結果集中包括“合計”的例程通常要比使用游標執(zhí)行的速度快。如果開發(fā)時間允許,基于游標的方法和基于集的方法都可以嘗試一下,看哪一種方法的效果更好。

  28. 在所有的存儲過程和觸發(fā)器的開始處設置 SET NOCOUNT ON ,在結束時設置 SET NOCOUNT OFF。無需在執(zhí)行存儲過程和觸發(fā)器的每個語句后向客戶端發(fā)送DONE_IN_PROC 消息。

  29. 盡量避免大事務操作,提高系統(tǒng)并發(fā)能力。

  30. 盡量避免向客戶端返回大數(shù)據(jù)量,若數(shù)據(jù)量過大,應該考慮相應需求是否合理。

看了以上介紹實踐中應該如何優(yōu)化MySQL,希望能給大家在實際運用中帶來一定的幫助。本文由于篇幅有限,難免會有不足和需要補充的地方,大家可以繼續(xù)關注創(chuàng)新互聯(lián)行業(yè)資訊板塊,會定期給大家更新行業(yè)新聞和知識,如有需要更加專業(yè)的解答,可在官網(wǎng)聯(lián)系我們的24小時售前售后,隨時幫您解答問題的。

網(wǎng)站欄目:實踐中應該如何優(yōu)化MySQL
文章路徑:http://bm7419.com/article22/gipgjc.html

成都網(wǎng)站建設公司_創(chuàng)新互聯(lián),為您提供App設計、自適應網(wǎng)站品牌網(wǎng)站建設、用戶體驗、域名注冊、網(wǎng)站導航

廣告

聲明:本網(wǎng)站發(fā)布的內容(圖片、視頻和文字)以用戶投稿、用戶轉載內容為主,如果涉及侵權請盡快告知,我們將會在第一時間刪除。文章觀點不代表本網(wǎng)站立場,如需處理請聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內容未經允許不得轉載,或轉載時需注明來源: 創(chuàng)新互聯(lián)

成都網(wǎng)站建設