1. 程式人生 > >資料庫學習進階一

資料庫學習進階一

一:問題的產生:

在應用系統開發初期,由於開發資料庫資料比較少,對於查詢SQL語句,複雜檢視的的編寫等體會不出SQL語句各種寫法的效能優劣,但是如果將應用系統提交實際應用後,隨著資料庫中資料的增加,系統的響應速度就成為目前系統需要解決的最主要的問題之一。系統優化中一個很重要的方面就是SQL語句的優化。對於海量資料,劣質SQL語句和優質SQL語句之間的速度差別可以達到上百倍,可見對於一個系統不是簡單地能實現其功能就可,而是要寫出高質量的SQL語句,提高系統的可用性。

原因分析

主要原因1:後臺資料庫中的資料過多,沒做資料優化導致後臺查詢資料很慢

次要原因2:前端資料請求-解析-展示過程處理不當

次要原因3:網路問題所致

那麼我們應該怎麼做後臺資料優化呢?

1、快取,在持久層或持久層之上做快取

使用ehcache快取,這個一般用於持久層的快取,提供持久層、業務層的快速快取,hibenate預設使用的二級快取就是ehcache;

2、資料庫表的大欄位剝離

假如一個表的欄位數有100多個,學會拆分欄位,保證單條記錄的資料量很小;

3、恰當地使用索引

必要時建立多級索引,分析MySQL的執行計劃,通過表資料統計等方式協助資料庫走正確的查詢方式,該走索引就走索引,該走全表掃描就走全表掃描;

4、表的拆分

表分割槽和拆分,無論是業務邏輯上的拆分(如一個月一張報表、分庫)還是無業務含義的分割槽(如根據ID取模分割槽);

5、欄位冗餘

減少跨庫查詢和大表連線操作;,資料通過單個或多個JOB生成出來,減少實時查詢;

6、從磁碟上做文章

資料存放的在磁碟的內、外磁軌上,資料獲取的效率都是不一樣的;

7、放棄關係資料庫的某些特性

引入NoSQL資料庫;

換種思路存放資料,例如搜尋中的倒排表;

在上面談到資料庫查詢速度優化方案我們講到了,資料優化的幾種方案。接下來,一起看如何實際到具體的操作上.也就是我們在寫資料時我們應該注意些什麼?

1、對查詢進行優化,應儘可能避免全表掃描

首先應考慮在 where 及 order by 涉及的列上建立索引。

下面我們來以一個表中177條資料比較一下,全表掃描與建立索引之後效能的一個比較.

1.1 全表查詢

select * from table

1.2 建立索引查詢

select * from table where pay = 1 and order by enter

1.3 結論

從這兩種方式查詢資料庫結果看,建立索引之後查詢速度提高了些,現在資料量還不明顯,如果表中有10萬條速度,差異就會很明顯了.

2、寫資料語句時儘可能減少表的全域性掃描

2.1 減少where 欄位值null判斷

select * from table where pay_status = null;

如何這樣做,就會導致引擎放棄使用索引而進行全表掃描

應該這樣去設定(也就是在沒有值時,我們在存資料庫時自動預設給個o值,而不是什麼都不寫):

select * from table where pay_status = 0;

2.2 應儘量避免在 where 子句中使用!=或<>操作符

select * from table where pay_status != 0;
select * from table where pay_status <> null;

這樣寫將導致引擎放棄使用索引而進行全表掃描。

2.3 應儘量避免在 where 子句中使用 or 來連線條件

select * from table where pay_status != null or entertime = null;

這樣將導致引擎放棄使用索引而進行全表掃描

可以這樣操作:

select * from table where pay_status != null union all
select * from table where entertime = null;

2.4 in 和 not in 也要慎用

select * from table where rowed in [1,2,3,4];
或者
select * from table where rowed not in [1,2,3,4];

這樣操作,也會導致全表掃描

select * from table where rowed between 1 and 5;

2.5 少使用模糊匹配like

select * from table where entertime like '%2016-09-08%';

2.6 儘量避免在where子句中對欄位進行表示式操作

select * from table where rowed/4 = 100

這樣寫將導致引擎放棄使用索引進行全盤掃描

select * from table where rowed = 4*100

任何時候都不要用萬用字元去查詢所有

以萬用字元*去查詢所有資料,這樣做也是非常耗時的,我們應該需要什麼欄位就查詢什麼欄位.