1.規劃
2.需求分析
3.概念模型設計
4.邏輯設計
5.物理設計
6.程序編制及調試
7.運行及維護。php
CREATE DATEBASE database_namejava
SHOW DATABASEmysql
USE database_namec++
DORP DATABASE database_nameweb
SHOW ENGINES;redis
SHOW VARIABLES LIKE ‘storage_engine%’sql
CRATE TABLE table_name(
Field_name data_type,
Field_name data_type,
…
Field_name data_type
)shell
DESC[RIBE] table_name數據庫
DROP TABLE table_name編程
ALTER TABLE old_table_name RENAME [TO] new_table_name
ALTER TABLE table_name ADD field_name data_type
SHOW CREATE TABLE table_name
ALTER TABLE table_name ADD field_name data_type FIRST
ALTER TABLE table_name ADD field_name data_type AFTER field_name
ALTER TABLE table_name DORP field_name
ALTER TABLE table_name MODIFY field_name data_type
ALTER TABLE table_name CHANGE old_field_name new_field_name old_data_type
ALTER TABLE table_name CHANGE old_field_name new_field_name new_data_type
ALTER TABLE table_name MODIFY field_name_1 data_type [FIRST]|[AFTER field_name_2]
Field_name data_type NOT NULL
Field_name data_type DEFAULT default_value
一、Field_name data_type UNIQUE
二、CONSTRAINT constraint_name UNIQUE(field_name)
Field_name data_type PRIMARY KEY
CONSTRAINT constraint_name PRIMARY KEY (field_name_1, field_name_2, …)
Field_name data_type AUTO_INCREMENT
CONSTRAINT constraint_name FOREIGN KEY(filed_name)
REFERENCES other_table_name(other_field_name)
[表示可先項]
|表示選擇
table_name(
column_name
INDEX|KEY [index_name](field_name [(index_length)] [ASC|DESC])
)
一、CREATE INDEX index_name ON table_name (
field_name [(index_length)] [ASC|DESC])
二、ALTER TABLE table_name ADD INDEX|KEY
index_name(field_name [(index_length)] [ASC|DESC])
table_name(
column_name
UNIQUE INDEX|KEY [index_name](
field_name [(index_length)] [ASC|DESC])
)
一、CREATE UNIQUE INDEX index_name ON table_name (
field_name [(index_length)] [ASC|DESC])
二、ALTER TABLE table_name ADD UNIQUE INDEX|KEY
index_name(field_name [(index_length)] [ASC|DESC])
table_name(
column_name
FULLTEXT INDEX|KEY [index_name](
field_name [(index_length)] [ASC|DESC])
)
一、CREATE FULLTEXT INDEX index_name ON table_name (
field_name [(index_length)] [ASC|DESC])
二、ALTER TABLE table_name ADD FULLTEXT INDEX|KEY
index_name(field_name [(index_length)] [ASC|DESC])
和上面的方法相似
index_name(field_name_1 [(index_length)] [ASC|DESC],
… ,
field_name_n [(index_length)] [ASC|DESC])
DROP INDEX index_name ON table_name
CREATE VIEW view_name AS select_query
SHOW TABLE STATUS [FROM database_name] [LIKE ‘pattern’]
DESC[RIBE] view_name
DROP VIEW view_name[, view_name]
一、CREATE OR REPLACE VIEW view_name AS select_query
二、ALTER VIEW view_name AS select_query
CREATE TIRGGER trigger_name
BEFORE|AFTER DELETE|INSERT|UPDATE
ON table_name FOR EACH ROW
Triggle_statement
Triggle_statement:觸發器被觸發要執行的語句(增、刪、改、查等等)
SHOW TRIGGERS
DROP TRIGGER trigger_name
INSERT INTO table_name (field_1, field_2, …) VALUES (value_1, value_2, vaule_3, …)
desc 表名;
show columns from 表名;
describe 表名;
show create table 表名;
use information_schema
select * from columns where table_name=’表名’;
select * from userdetail where userid limit 0,20
(mysql-5.5.5開始,InnoDB做爲默認存儲引擎)以前是MyISAM,更早是ISAM你能用的數據庫引擎取決於mysql在安裝的時候是如何被編譯的。要添加一個新的引擎,就必須從新編譯MYSQL。在缺省狀況下,MYSQL支持三個引擎:ISAM、MYISAM和HEAP。另外兩種類型INNODB和BERKLEYDB(BDB), 也經常能夠使用。
ISAM是一個定義明確且歷經時間考驗的數據表格管理方法,它在設計之時就考慮到數據庫被查詢的次數要遠大於更新的次數。所以,ISAM執行讀取操做的速度很快,並且不佔用大量的內存和存儲資源。ISAM的兩個主要不足之處在於,它不支持事務處理,也不可以容錯:若是你的硬盤崩潰了,那麼數據文件就沒法恢復了。若是你正在把ISAM用在關鍵任務應用程序裏,那就必須常常備份你全部的實時數據,經過其複製特性,MYSQL可以支持這樣的備份應用 程序。
MYISAM是MYSQL的ISAM擴展格式和缺省的數據庫引擎(5.5以前)。除了提供ISAM裏所沒有的索引和字段管理的大 量功能,MYISAM還使用一種表格鎖定的機制,來優化多個併發的讀寫操做。其代價是你須要常常運行OPTIMIZE TABLE命令,來恢復被更新機制所浪費的空間。MYISAM還有一些有用的擴展,例如用來修復數據庫文件的 MYISAMCHK工具和用來恢復浪費空間的MYISAMPACK工具。
MYISAM強調了快速讀取操做,這可能就是爲何MYSQL受到了WEB開發如此青睞的主要緣由:在WEB開發中你所進行的大量數據操做都是讀取操做。因此,大多數虛擬主機提供商和INTERNET平臺提供商只容許使用MYISAM格式。
HEAP容許只駐留在內存裏的臨時表格。駐留在內存使得HEAP比ISAM和MYISAM的速度都快,可是它所管理的數據是不穩定的,並且若是在關機以前沒有進行保存,那麼全部的數據都會丟失。在數據行被刪除的時候,HEAP也不會浪費大量的空間,HEAP表格在你須要使用SELECT表達式來選擇和操控數據的時候很是有用。要記住,用完表格後要刪除表格。
INNODB和BERKLEYDB(BDB)數據庫引擎都是造就MYSQL靈活性的技術的直接產品,這項技術就是MySql++ API。在使用MySql的時候,你所面對的每個挑戰幾乎都源於ISAM和MYIASM數據庫引擎不支持事務處理也不支持外來鍵。儘管要比ISAM和MYISAM引擎慢不少,可是INNODB和BDB包括了對事務處理和外來鍵的支持,這兩點都是前兩個引擎所沒有的。如前所述,若是你的設計須要這些特性中的一者或者二者,那你就要被迫使用後兩個引擎中的一個了。
根據鎖的類型分,能夠分爲共享鎖,排他鎖,意向共享鎖和意向排他鎖。
根據鎖的粒度分,又能夠分爲行鎖,表鎖。
對於mysql而言,事務機制更可能是靠底層的存儲引擎來實現,所以,mysql層面只有表鎖,而支持事務的innodb存 儲引擎則實現了行鎖(記錄鎖(在行相應的索引記錄上的鎖)),gap鎖(是在索引記錄間歇上的鎖),next-key鎖(是記錄鎖和在此索引記錄以前的gap上的鎖的結合)。Mysql的記錄鎖實質是索引記錄的鎖,由於innodb是索引組織表;gap鎖是索引記錄間隙的鎖,這種鎖只在RR隔離級別下有效;next-key鎖是記錄鎖加上記錄以前gap鎖的組合。mysql經過gap鎖和next-key鎖實現RR隔離級別。
說明:對於更新操做(讀不上鎖),只有走索引纔可能上行鎖;不然會對聚簇索引的每一行上寫鎖,實際等同於對錶上寫鎖。
若多個物理記錄對應同一個索引,若同時訪問,也會出現鎖衝突;
當表有多個索引時,不一樣事務能夠用不一樣的索引鎖住不一樣的行,另外innodb會同時用行鎖對數據記錄(聚簇索引)加 鎖。
MVCC(多版本併發控制)併發控制機制下,任何操做都不會阻塞讀操做,讀操做也不會阻塞任何操做,只由於讀不上鎖。
共享鎖:由讀表操做加上的鎖,加鎖後其餘用戶只能獲取該表或行的共享鎖,不能獲取排它鎖,也就是說只能讀不能寫
排它鎖:由寫表操做加上的鎖,加鎖後其餘用戶不能獲取該表或行的任何鎖,典型是mysql事務中的更新操做
意向共享鎖(IS):事務打算給數據行加行共享鎖,事務在給一個數據行加共享鎖前必須先取得該表的IS鎖。
意向排他鎖(IX):事務打算給數據行加行排他鎖,事務在給一個數據行加排他鎖前必須先取得該表的IX鎖。
在缺省模式下,MYSQL是autocommit模式的,全部的數據庫更新操做都會即時提交,因此在缺省狀況下,mysql是不支持事務的。 可是若是你的MYSQL表類型是使用InnoDB Tables 或 BDB tables的話,你的MYSQL就能夠使用事務處理,使用SET AUTOCOMMIT=0就能夠使MYSQL容許在非autocommit模式, 在非autocommit模式下,你必須使用COMMIT來提交你的更改,或者用ROLLBACK來回滾你的更改。
示例以下:
START TRANSACTION;
SELECT @A:=SUM(salary) FROM table1 WHERE type=1;
UPDATE table2 SET summmary=@A WHERE type=1;
COMMIT;
一、能夠處理擁有上千萬條記錄的大型數據
二、支持常見的SQL語句規範
三、可移植行高,安裝簡單小巧
四、良好的運行效率,有豐富信息的網絡支持
五、調試、管理,優化簡單(相對其餘大型數據庫)
一、在數據庫安裝的時候指定字符集
二、若是在安完了之後能夠更改以配置文件
三、創建數據庫時候:指定字符集類型
四、建表的時候也指定字符集
1.若是MYSQL客戶端和服務器端的鏈接須要跨越並經過不可信任的網絡,那麼須要使用ssh隧道來加密該鏈接的通訊。
2.使用set password語句來修改用戶的密碼,先「mysql -u root」登錄數據庫系統,而後mysql> update mysql.user set password=password(‘newpwd’),最後執行flush privileges就能夠了。
3.Mysql須要提防的攻擊有,防偷聽、篡改、回放、拒絕服務等,不涉及可用性和容錯方面。對全部的鏈接、查詢、其餘操做使用基於acl即訪問控制列表的安全措施來完成。也有一些對ssl鏈接的支持。
4.設置除了root用戶外的其餘任何用戶不容許訪問mysql主數據庫中的user表; 加密後存放在user表中的加密 後的用戶密碼一旦泄露,其餘人能夠隨意用該用戶名/密碼相應的數據庫;
5.使用grant和revoke語句來進行用戶訪問控制的工做;
6.不要使用明文密碼,而是使用md5()和sha1()等單向的哈系函數來設置密碼;
7.不要選用字典中的字來作密碼;
8.採用防火牆能夠去掉50%的外部危險,讓數據庫系統躲在防火牆後面工做,或放置在dmz區域中;
9.從因特網上用nmap來掃描3306端口,也可用telnet server_host 3306的方法測試,不容許從非信任網絡中訪問數據庫服務器的3306號tcp端口,須要在防火牆或路由器上作設定;
10.爲了防止被惡意傳入非法參數,例如where id=234,別人卻輸入where id=234 or 1=1致使所有顯示,因此在web的表單中使用」或」」來用字符串,在動態url中加入%22表明雙引號、%23表明井號、%27表明單引號;傳遞未檢查過的值給mysql數據庫是很是危險的;
11.在傳遞數據給mysql時檢查一下大小;
12.應用程序須要鏈接到數據庫應該使用通常的用戶賬號,開放少數必要的權限給該用戶; pagedevidepagedevide
13.在各編程接口(c c++ php perl java jdbc等)中使用特定‘逃脫字符’函數; 在因特網上使用mysql數據 庫時必定少用傳輸明文的數據,而用ssl和ssh的加密方式數據來傳輸;
14.學會使用tcpdump和strings工具來查看傳輸數據的安全性,例如tcpdump -l -i eth0 -w -src or
dst port 3306 strings。以普通用戶來啓動mysql數據庫服務;
15.不使用到表的聯結符號,選用的參數 –skip-symbolic-links;
16.確信在mysql目錄中只有啓動數據庫服務的用戶才能夠對文件有讀和寫的權限;
17.不準將process或super權限付給非管理用戶,該mysqladmin processlist能夠列舉出當前執行的查詢 文本;super權限可用於切斷客戶端鏈接、改變服務器運行參數狀態、控制拷貝複製數據庫的服務器;
18.file權限不付給管理員之外的用戶,防止出現load data ‘/etc/passwd’到表中再用select 顯示出來
的問題;
19.若是不相信dns服務公司的服務,能夠在主機名稱容許表中只設置ip數字地址;
20.使用max_user_connections變量來使mysqld服務進程,對一個指定賬戶限定鏈接數;
21.grant語句也支持資源控制選項;
22.–local-infile=0或1 如果0則客戶端程序就沒法使用local load data了,賦權的一個例子grant insert(user) on mysql.user to ‘user_name’@’host_name’;若使用–skip-grant-tables系統將對任何用戶的訪問不作任何訪問控制,但能夠用 mysqladmin flush-privileges或mysqladmin reload來開啓訪問控制;默認狀況是show databases語句對全部用戶開放,能夠用–skip-show-databases來關閉掉。
23.碰到error 1045(28000) access denied for user ‘root’@’localhost’ (using password:no)錯誤時,你須要從新設置密碼,具體方法是:先用–skip-grant-tables參數啓動mysqld,而後執行 mysql -u root mysql,mysql>update user set password=password(’newpassword’) where user=’root’;mysql>flush privileges;,最後從新啓動mysql就能夠了。
取得當前時間用 now() 就行。在數據庫中格式化時間 用DATE_FORMAT(date, format)。根據格式串
format 格式化日期或日期時間值date,返回結果串。
答案: Debian 上運行命令 service mysql status,在RedHat 上運行命令 service mysqld status。而後看看輸出便可。
答案:運行命令 service mysqld start 開啓服務;運行命令 service mysqld stop 中止服務。
答案:運行命令 mysql -u root –p
答案:運行命令 show databases;
答案:運行命令 use database_name; 進入名爲 database_name 的數據庫。
答案:在當前數據庫運行命令 show tables;
答案:運行命令 describe table_name;
答案:運行命令 drop table table_name;
對於查詢佔主要的應用來講,索引顯得尤其重要。不少時候性能問題很簡單的就是由於咱們忘了添加索引而形成的,或者說沒有添加更爲有效的索引致使。若是不加索引的話,那麼查找任何哪怕只是一條特定的數據都會進行一次全表掃描,若是一張表的數據量很大而符合條件的結果又不多,那麼不加索引會引發致命的性能降低。可是也不是什麼情 況都非得建索引不可,好比性別可能就只有兩個值,建索引不只沒什麼優點,還會影響到更新速度,這被稱爲過分索引。
好比有一條語句是這樣的:select * from users where area=’beijing’ and age=22;
若是咱們是在area和age上分別建立單個索引的話,因爲mysql查詢每次只能使用一個索引,因此雖然這樣已經相對不作索引時全表掃描提升了不少效率,可是若是在area、age兩列上建立複合索引的話將帶來更高的效率。若是咱們建立了(area, age, salary)的複合索引,那麼其實至關於建立了(area,age,salary)、 (area,age)、(area)三個索引,這被稱爲最佳左前綴特性。所以咱們在建立複合索引時應該將最經常使用做限制條件的列放在最左邊,依次遞減。
只要列中包含有NULL值都將不會被包含在索引中,複合索引中只要有一列含有NULL值,那麼這一列對於此複合索引就是無效的。因此咱們在數據庫設計時不要讓字段的默認值爲NULL。
對串列進行索引,若是可能應該指定一個前綴長度。例如,若是有一個CHAR(255)的列,若是在前10個或20個字符內,多數值是唯一的,那麼就不要對整個列進行索引。短索引不只能夠提升查詢速度並且能夠節省磁盤空間和I/O操做。
mysql查詢只使用一個索引,所以若是where子句中已經使用了索引的話,那麼order by中的列是不會使用索引的。所以數據庫默認排序能夠符合要求的狀況下不要使用排序操做;儘可能不要包含多個列的排序,若是須要最好給這些列建立複合索引。
通常狀況下不鼓勵使用like操做,若是非使用不可,如何使用也是一個問題。like 「%aaa%」 不會使用索引而like 「aaa%」能夠使用索引。
VARCHAR和CHAR類型,varchar是變長的,須要額外的1-2個字節存儲,能節約空間,可能會對性能有幫助。但因爲是變長,可能發生碎片,如更新數據;
使用ENUM(MySQL的枚舉類)代替字符串類型,數據實際存儲爲整型。
字符串類型
要儘量地避免使用字符串來作標識符,由於它們佔用了不少空間而且一般比整數類型要慢。特別注意不要在MYISAM表上使用字符串標識符。MYISAM默認狀況下爲字符串使用了壓縮索引(Packed Index),這使查找更爲緩慢。據測試,使用了壓縮索引的MYISAM表性能要慢6倍。
還要特別注意徹底‘隨機’的字符串,例如由MD5()、SHA1()、UUID()產生的。它們產生的每個新值都會被任意地保存在很大的空間範圍內,這會減慢INSERT及一些SELECT查詢。1)它們會減慢INSERT查詢,由於插入的值會被隨機地放入索引中。這會致使分頁、隨機磁盤訪問及彙集存儲引擎上的彙集索引碎片。2)它們會減慢SELECT查詢,由於邏輯上相鄰的行會分佈在磁盤和內存中的各個地方。3)隨機值致使緩存對全部類型的查詢性能都不好,由於它們會使緩存賴以工做的訪問局部性失效。若是整個數據集都變得一樣「熱」的時候,那麼把特定部分的數據緩存到內存中就沒有任何的優點了。而且若是工做集不能被裝入內存中,緩存就會進行不少刷寫的工做,而且會致使不少緩存未命中。
若是保存UUID值,就應該移除其中的短橫線,更好的辦法是使用UHEX()把UUID值轉化爲16字節的數字,並把它保存在BINARY(16)列中。
select * from users where YEAR(adddate)<2007;
將在每一個行上進行運算,這將致使索引失效而進行全表掃描,所以咱們能夠改爲
select * from users where adddate<‘2007-01-01’;
不使用NOT IN和操做
NOT IN和操做都不會使用索引將進行全表掃描。NOT IN能夠NOT EXISTS代替,id != 3則可以使用id>3 or id<3來代替。
不能用null做索引,任何包含null值的列都將不會被包含在索引中。即便索引有多列這樣的狀況下,只要這些列中有一列含有null,該列就會從索引中排除。也就是說若是某列存在空值,即便對該列建索引也不會提升性能。
任何在where子句中使用is null或is not null的語句優化器是不容許使用索引的。
對於有聯接的列,即便最後的聯接值爲一個靜態值,優化器是不會使用索引的。
一、邏輯備份:使用mysql自帶的mysqldump工具進行備份。備份成sql文件形式。
優勢:最大好處是可以與正在運行的mysql自動協同工做,在運行期間能夠確保備份是當時的點,它會自動將對應操做的表鎖定,不容許其餘用戶修改(只能訪問)。可能會阻止修改操做。sql文件通用方便移植。
缺點:備份的速度比較慢。若是是數據量不少的時候。就很耗時間。若是數據庫服務器處在提供給用戶服務狀態,在這段長時間操做過程當中,意味着要鎖定表(通常是讀鎖定,只能讀不能寫入數據)。那麼服務就會影響的。
二、物理備份:直接拷貝mysql的數據目錄。
直接拷貝只適用於myisam類型的表。這種類型的表是與機器獨立的。但實際狀況是,你設計數據庫的時候不可能所有使用myisam類型表。你也不可能由於myisam類型表與機器獨立,方便移植,因而就選擇這種表,這並非選擇它的理由。
缺點:你不能去操做正在運行的mysql服務器(在拷貝的過程當中有用戶經過應用程序訪問更新數據,這樣就沒法備份當時的數據)可能沒法移植到其餘機器上去。
三、雙機熱備份。
mysql數據庫沒有增量備份的機制。當數據量太大的時候備份是一個很大的問題。還好mysql數據庫提供了一種主從備份的機制(也就是雙機熱備)
優勢:適合數據量大的時候。如今明白了。大的互聯網公司對於mysql數據備份,都是採用熱機備份。搭建多臺數據庫服務器,進行主從複製。
explain顯示了mysql如何使用索引來處理select語句以及鏈接表。能夠幫助選擇更好的索引和寫出更優化的查詢語句。使用方法,在select語句前加上explain就能夠了。因此使用explain能夠查看。
能夠使用邏輯備份和雙機熱備份。
徹底備份:完整備份通常一段時間進行一次,且在網站訪問量最小的時候,這樣常藉助批處理文件定時備份。主要是寫一個批處理文件在裏面寫上處理程序的絕對路徑而後把要處理的東西寫在後面,即徹底備份數據庫。
增量備份:對ddl和dml語句進行二進制備份。且5.0沒法增量備份,5.1後能夠。若是要實現增量備份須要在my.ini文件中配置備份路徑便可,重啓mysql服務器,增量備份就啓動了。
普通索引 添加INDEX
ALTER TABLE ‘table_name’ ADD INDEX index_name (‘column’);
主鍵索引 添加PRIMARY KEY
ALTER TABLE ‘table_name’ ADD PRIMARY KEY (‘column’);
惟一索引 添加UNIQUE
ALTER TABLE ‘table_name’ ADD UNIQUE (‘column’);
全文索引 添加FULLTEXT
ALTER TABLE ‘table_name’ ADD FULLTEXT (‘column’);
多列索引
ALTER TABLE ‘table_name’ ADD INDEX index_name (‘column1’, ‘column2’, ‘column3’)
表的主關鍵字
自動創建惟一索引
如zl_yhjbqk(用戶基本狀況)中的hbs_bh(戶標識編號)
表的字段惟一約束
ORACLE利用索引來保證數據的完整性
如lc_hj(流程環節)中的lc_bh+hj_sx(流程編號+環節順序)
直接條件查詢的字段
在SQL中用於條件約束的字段
如zl_yhjbqk(用戶基本狀況)中的qc_bh(區冊編號)
select * from zl_yhjbqk where qc_bh=’7001’
查詢中與其它表關聯的字段
字段經常創建了外鍵關係
如zl_ydcf(用電成份)中的jldb_bh(計量點表編號)
select * from zl_ydcf a,zl_yhdb b where a.jldb_bh=b.jldb_bh and b.jldb_bh=’540100214511’
查詢中排序的字段
排序的字段若是經過索引去訪問那將大大提升排序速度
select * from zl_yhjbqk order by qc_bh(創建qc_bh索引)
select * from zl_yhjbqk where qc_bh=’7001’ order by cb_sx(創建qc_bh+cb_sx索引,注:只是一個索引,其中包括qc_bh和cb_sx字段)
查詢中統計或分組統計的字段
select max(hbs_bh) from zl_yhjbqk
select qc_bh,count(*) from zl_yhjbqk group by qc_bh
表記錄太少
若是一個表只有5條記錄,採用索引去訪問記錄的話,那首先需訪問索引表,再經過索引表訪問數據表,通常索引表與數據表不在同一個數據塊,這種狀況下ORACLE至少要往返讀取數據塊兩次。而不用索引的狀況下ORACLE會將全部的數據一次讀出,處理速度顯然會比用索引快。
如表zl_sybm(使用部門)通常只有幾條記錄,除了主關鍵字外對任何一個字段建索引都不會產生性能優化,實際上若是對這個表進行了統計分析後ORACLE也不會用你建的索引,而是自動執行全表訪問。如:select * from zl_sybm where sydw_bh=’5401’(對sydw_bh創建索引不會產生性能優化)
常常插入、刪除、修改的表
對一些常常處理的業務表應在查詢容許的狀況下儘可能減小索引,如zl_yhbm,gc_dfss,gc_dfys,gc_fpdy等業務表。
數據重複且分佈平均的表字段
假如一個表有10萬行記錄,有一個字段A只有T和F兩種值,且每一個值的分佈機率大約爲50%,那麼對這種表A字段建索引通常不會提升數據庫的查詢速度。
常常和主字段一塊查詢但主字段索引值比較多的表字段
如gc_dfss(電費實收)表常常按收費序號、戶標識編號、抄表日期、電費發生年月、操做 標誌來具體查詢某一筆收款的狀況,若是將全部的字段都建在一個索引裏那將會增長數據的修改、插入、刪除時間,從實際上分析一筆收款若是按收費序號索引就已 經將記錄減小到只有幾條,若是再按後面的幾個字段索引查詢將對性能不產生太大的影 響。
1.對查詢進行優化,應儘可能避免全表掃描,首先應考慮在 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) 對於連續的數值,能用 between 就不要用 in 了:select id from t where num between 1 and 3
6.避免使用通配符。下面的查詢也將致使全表掃描:select id from t where name like ‘李%’若要提升效率,能夠考慮全文檢索。
7.若是在 where 子句中使用參數,也會致使全表掃描。由於SQL只有在運行時纔會解析局部變量,但優化程序不能將訪問計劃的選擇推遲到運行時;它必須在編譯時進行選擇。然而,若是在編譯時創建訪問計劃,變量的值仍是未知的,於是沒法做爲索引選擇的輸入項。以下面語句將進行全表掃描: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子句中對字段進行函數操做,這將致使引擎放棄使用索引而進行全表掃描。如:select id from t where substring(name,1,3)=’abc’ ,name以abc開頭的id應改成:select id from t where name like ‘abc%’
10.不要在 where 子句中的「=」左邊進行函數、算術運算或其餘表達式運算,不然系統將可能沒法正確使用索引。
11.在使用索引字段做爲條件時,若是該索引是複合索引,那麼必須使用到該索引中的第一個字段做爲條件時才能保證系統使用該索引,不然該索引將不會被使用,而且應儘量的讓字段順序與索引順序相一致。
12.不要寫一些沒有意義的查詢,如須要生成一個空表結構:select col1,col2 into #t from t where 1=0 這類代碼不會返回任何結果集,可是會消耗系統資源的,應改爲這樣: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是根據表中數據來進行查詢優化的,當索引列有大量數據重複時,SQL查詢可能不會去利用索引,如一表中有字段sex,male、female幾乎各一半,那麼即便在sex上建了索引也對查詢效率起不了做用。
15.索引並非越多越好,索引當然能夠提升相應的 select 的效率,但同時也下降了insert 及 update 的 效率,由於 insert 或 update 時有可能會重建索引,因此怎樣建索引須要慎重考慮,視具體狀況而定。一個表的索引數最好不要超過6個,若太多則應考慮一些不常使用到的列上建的索引是否有 必要。
16.應儘量的避免更新 clustered 索引數據列,由於 clustered 索引數據列的順序就是表記錄的物理存儲 順序,一旦該列值改變將致使整個表記錄的順序的調整,會耗費至關大的資源。若應用系統須要頻繁更新 clustered 索引數據列,那麼須要考慮是否應將該索引建爲 clustered 索引。
17.儘可能使用數字型字段,若只含數值信息的字段儘可能不要設計爲字符型,這會下降查詢和鏈接的性能,並會增長存儲開銷。這是由於引擎在處理查詢和鏈接時會逐個比較字符串中每個字符,而對於數字型而言只須要比較一次就夠了。
18.儘量的使用 varchar/nvarchar 代替 char/nchar ,由於首先變長字段存儲空間小,能夠節省存儲空間,其次對於查詢來講,在一個相對較小的字段內搜索效率顯然要高些。
19.任何地方都不要使用 select * from t ,用具體的字段列表代替「*」,不要返回用不到的任何字段。
20.儘可能使用表變量來代替臨時表。若是表變量包含大量數據,請注意索引很是有限(只有主鍵索引)。
21.避免頻繁建立和刪除臨時表,以減小系統表資源的消耗。
22.臨時表並非不可以使用,適當地使用它們能夠使某些例程更有效,例如,當須要重複引用大型表或經常使用表中的某個數據集時。可是,對於一次性事件,最好使用導出表。
23.在新建臨時表時,若是一次性插入數據量很大,那麼能夠使用 select into 代替 create table,避免形成大量 log ,以提升速度;若是數據量不大,爲了緩和系統表的資源,應先create table,而後insert。
24.若是使用到了臨時表,在存儲過程的最後務必將全部的臨時表顯式刪除,先 truncate table ,而後 drop table ,這樣能夠避免系統表的較長時間鎖定。
25.儘可能避免使用遊標,由於遊標的效率較差,若是遊標操做的數據超過1萬行,那麼就應該考慮改寫。
26.使用基於遊標的方法或臨時表方法以前,應先尋找基於集的解決方案來解決問題,基於集的方法一般更有效。
27.與臨時表同樣,遊標並非不可以使用。對小型數據集使用 FAST_FORWARD 遊標一般要優於其餘逐行處理方法,尤爲是在必須引用幾個表才能得到所需的數據時。在結果集中包括「合計」的例程一般要比使用遊標執行的速度快。若是開發時間容許,基於遊標的方法和基於集的方法均可以嘗試一下,看哪種方法的效果更好。
28.在全部的存儲過程和觸發器的開始處設置 SET NOCOUNT ON ,在結束時設置 SET NOCOUNT OFF。無需在執行存儲過程和觸發器的每一個語句後向客戶端發送DONE_IN_PROC 消息。
29.儘可能避免大事務操做,提升系統併發能力。
30.儘可能避免向客戶端返回大數據量,若數據量過大,應該考慮相應需求是否合理。
1,建立索引
對於查詢佔主要的應用來講,索引顯得尤其重要。不少時候性能問題很簡單的就是由於咱們忘了添加索引而形成的,或者說沒有添加更爲有效的索引致使。若是不加索引的話,那麼查找任何哪怕只是一條特定的數據都會進行一次全表掃描,若是一張表的數據量很大而符合條件的結果又不多,那麼不加索引會引發致命的性能降低。可是也不是什麼狀況都非得建索引不可,好比性別可能就只有兩個值,建索引不只沒什麼優點,還會影響到更新速度,這被稱爲過分索引。
2,複合索引
好比有一條語句是這樣的:select * from users where area=’beijing’ and age=22;
若是咱們是在area和age上分別建立單個索引的話,因爲mysql查詢每次只能使用一個索引,因此雖然這樣已經相對不作索引時全表掃描提升了不少效率,可是若是在area、age兩列上建立複合索引的話將帶來更高的效率。若是咱們建立了(area, age,salary)的複合索引,那麼其實至關於建立了(area,age,salary)、(area,age)、(area)三個索引,這被稱爲最佳左前綴特性。所以咱們在建立複合索引時應該將最經常使用做限制條件的列放在最左邊,依次遞減。
3,索引不會包含有NULL值的列
只要列中包含有NULL值都將不會被包含在索引中,複合索引中只要有一列含有NULL值,那麼這一列對於此複合索引就是無效的。因此咱們在數據庫設計時不要讓字段的默認值爲NULL。
4,使用短索引
對串列進行索引,若是可能應該指定一個前綴長度。例如,若是有一個CHAR(255)的 列,若是在前10 個或20 個字符內,多數值是唯一的,那麼就不要對整個列進行索引。短索引不只能夠提升查詢速度並且能夠節省磁盤空間和I/O操做。
5,排序的索引問題
mysql查詢只使用一個索引,所以若是where子句中已經使用了索引的話,那麼order by中的列是不會使用索引的。所以數據庫默認排序能夠符合要求的狀況下不要使用排序操做;儘可能不要包含多個列的排序,若是須要最好給這些列建立複合索引。
6,like語句操做
通常狀況下不鼓勵使用like操做,若是非使用不可,如何使用也是一個問題。like 「%aaa%」 不會使用索引而like 「aaa%」能夠使用索引。
7,不要在列上進行運算
select * from users where YEAR(adddate)
8,不使用NOT IN和操做
NOT IN和操做都不會使用索引將進行全表掃描。NOT IN能夠NOT EXISTS代替,id != 3則可以使用id>3 or id < 3
一、show processlist;
二、select * from information_schema.processlist ;
三、能夠在[mysqld]中添加以下:
log =/var/log/mysql.log
若是須要監控慢查詢能夠添加以下內容:
log-slow-queries = /var/log/slowquery.log
long_query_time = 1
術語「彙集」指實際的數據行和相關的鍵值都保存在一塊兒。每一個表只能有一個彙集索引。可是,覆蓋索引能夠模擬多個彙集索引。存儲引擎負責實現索引,所以不是全部的存儲索引都支持彙集索引。當前,SolidDB和InnoDB是惟一支持彙集索引的存儲引擎。
優勢:
能夠把相關數據保存在一塊兒。這樣從磁盤上提取幾個頁面的數據就能把某個用戶的數據所有抓取出來。若是沒有使用匯集,讀取每一個數據都會訪問磁盤。
數據訪問快。彙集索引把索引和數據都保存到了同一棵B-TREE中,所以從彙集索引中取得數據一般比在非彙集索引進行查找要快。
缺點:
彙集能最大限度地提高I/O密集負載的性能。若是數據能裝入內存,那麼其順序也就無所謂了。這樣彙集就沒有什麼用處。
插入速度嚴重依賴於插入順序。更新彙集索引列是昂貴的,由於強制InnoDB把每一個更新的行移到新的位置。
創建在彙集索引上的表在插入新行,或者在行的主鍵被更新,該行必須被移動的時候會進行分頁。
彙集表可會比全表掃描慢,尤爲在表存儲得比較稀疏或由於分頁而沒有順序存儲的時候。
第二(非彙集)索引可能會比預想的大,由於它們的葉子節點包含了被引用行的主鍵列。第二索引訪問須要兩次索引查找,而不是一次。 InnoDB的第二索引葉子節點包含了主鍵值做爲指向行的「指針」,而不是「行指針」。 這種策略減小了在移動行或數據分頁的時候索引的維護工做。使用行的主鍵值做爲指針使得索引變得更大,可是這意味着InnoDB能夠移動行,而無須更新指針。
索引類型: B-TREE索引,哈希索引
B-TREE索引(默認的索引類型)加速了數據訪問,由於存儲引擎不會掃描整個表獲得須要的數據。相反,它從根節點開始。根節點保存了指向子節點的指針,而且存儲引擎會根據指針尋找數據。它經過查找節點頁中的值找到正確的指針,節點頁包含子節點的指針,而且存儲引擎會根據指針尋找數據。它經過查找節點頁中的值找到正確的指針,節點頁包含子節點中值的上界和下界。最後,存儲引擎可能沒法找到須要的數據,也可能成功地找到包含數據的葉子頁面。
例:B-TREE索引 對於如下類型查詢有用。匹配全名、匹配最左前綴、匹配列前綴、匹配範圍值、精確匹配一部分而且匹配某個範圍中的另外一部分;
B-TREE索引的侷限:若是查找沒有從索引列的最左邊開始,它就沒什麼用處。不能跳過索引中的列,存儲引擎不能優先訪問任何在第一個範圍條件右邊的列。例:若是查詢是where last_name=’Smith’ AND first_name LIKE ‘J%’ AND dob=’1976-12-23’;訪問就只能使用索引的頭兩列,由於LIKE是範圍條件。
哈希索引創建在哈希表的基礎上,它只對使用了索引中的每一列的精確查找有用。對於每一行,存儲引擎計算出了被索引列的哈希碼,它是一個較小的值,而且有可能和其餘行的哈希碼不一樣。它把哈希碼保存在索引中,而且保存了一個指向哈希表中每一行的指針。
由於索引只包含了哈希碼和行指針,而不是值自身,MYSQL不能使用索引中的值來避免讀取行。
MYSQL不能使用哈希索引進行排序,由於它們不會按序保存行。
哈希索引不支持部分鍵匹配,由於它們是由被索引的所有值計算出來的。也就是說,若是在(A,B)兩列上有索引,而且WHERE子句中只使用了A,那麼索引就不會起做用。
哈希索引只支持使用了= IN()和<=>的相等比較。它們不能加快範圍查詢。例如WHERE price > 100;
訪問哈希索引中的數據很是快,除非碰撞率很高。當發生碰撞的時候,存儲引擎必須訪問鏈表中的每個行指針,而後逐行進行數據比較,以肯定正確的數據。若是有不少碰撞,一些索引維護操做就有可能會變慢。
即爲全文索引,目前只有MyISAM引擎支持。其能夠在CREATE TABLE ,ALTER TABLE ,CREATE INDEX 使用,不過目前只有 CHAR、VARCHAR ,TEXT 列上能夠建立全文索引。值得一提的是,在數據量較大時候,現將數據放入一個沒有全局索引的表中,而後再用CREATE INDEX建立FULLTEXT索引,要比先爲一張表創建FULLTEXT而後再將數據寫入的速度快不少。FULLTEXT索引也是按照分詞原理創建索引的。西文中,大部分爲字母文字,分詞能夠很方便的按照空格進行分割。中文不能按照這種方式進行分詞。Mysql的中文分詞插件Mysqlcft,有了它,就能夠對中文進行分詞。
1、在編譯時優化MySQL
若是你從源代碼分發安裝MySQL,要注意,編譯過程對之後的目標程序性能有重要的影響,不一樣的編譯方式可能獲得相似的目標文件,但性能可能相差很大,所以,在編譯安裝MySQL適應仔細根據你的應用類型選擇最可能好的編譯選項。這種定製的MySQL能夠爲你的應用提供最佳性能。
技巧:選用較好的編譯器和較好的編譯器選項,這樣應用可提升性能10-30%。(MySQL文檔如是說)
1.一、使用pgcc(Pentium GCC)編譯器->(使用合適的編譯器)
該編譯器(http://www.goof.com/pcg/)針對運行在奔騰處理器系統上的程序進行優化,用pgcc編譯MySQL源代碼,整體性能可提升10%。固然若是你的服務器不是用奔騰處理器,就沒必要用它了,由於它是專爲奔騰系統設計的。
1.二、僅使用你想使用的字符集編譯MySQL
MySQL目前提供多達24種不一樣的字符集,爲全球用戶以他們本身的語言插入或查看錶中的數據。卻省狀況下,MySQL安裝全部者這些字符集,熱然而,最好的選擇是指選擇一種你須要的。如,禁止除Latin1字符集之外的全部其它字符集:
1.三、將mysqld編譯成靜態執行文件
將mysqld編譯成靜態執行文件而無需共享庫也能得到更好的性能。經過在配置時指定下列選項,可靜態編譯mysqld。
1.四、配置樣本
2、調整服務器
3、表類型(MySQL中表的類型)
不少MySQL用戶可能很驚訝,MySQL確實爲用戶提供5種不一樣的表類型,稱爲DBD、HEAP、ISAM、MERGE和MyIASM。DBD歸爲事務安全類,而其餘爲非事務安全類。
3.一、事務安全
DBD
Berkeley DB(DBD)表是支持事務處理的表,它提供MySQL用戶期待已久的功能-事務控制。事務控制在任何數據庫系統中都是一個極有價值的功能,由於它們確保一組命令能成功地執行。
3.二、非事務安全
HEAP
HEAP表是MySQL中存取數據最快的表。這是由於他們使用存儲在動態內存中的一個哈希索引。另外一個要點是若是MySQL或服務器崩潰,數據將丟失。
ISAM
ISAM表是早期MySQL版本的缺省表類型,直到MyIASM開發出來。建議不要再使用它。
MERGE
MERGE是一個有趣的新類型,在3.23.25以後出現。一個MERGE表其實是一個相同MyISAM表的集合,合併成一個表,主要是爲了效率緣由。這樣能夠提升速度、搜索效率、修復效率並節省磁盤空間。
MyIASM
這是MySQL的缺省表類型(5.5.5以前)。它基於IASM代碼,但有不少有用的擴展。MyIASM比較好的緣由:
MyIASM表小於IASM表,因此使用較少資源。
MyIASM表在不一樣的平臺上二進制層可移植。
更大的鍵碼尺寸,更大的鍵碼上限。
3.三、指定表類型
4、優化工具
MySQL服務器自己提供了幾條內置命令用於幫助優化。
4.一、SHOW
SHOW還能作更多的事情。它能夠顯示關於日誌文件、特定數據庫、表、索引、進程和權限表中有價值的信息。
4.二、EXPLAIN
當你面對SELECT語句時,EXPLAIN解釋SELECT命令如何被處理。這不只對決定是否應該增長一個索引,並且對決定一個複雜的Join如何被MySQL處理都是有幫助的。
4.三、OPTIMIZE
OPTIMIZE語句容許你恢復空間和合並數據文件碎片,對包含變長行的表進行了大量更新和刪除後,這樣作特別重要。OPTIMIZE目前只工做於MyIASM和BDB表。
innodb_buffer_pool_size:這是你安裝完InnoDB後第一個應該設置的選項。緩衝池是數據和索引緩存的地方:這個值越大越好,這能保證你在大多數的讀取操做時使用的是內存而不是硬盤。典型的值是5-6GB(8GB內存),20-25GB(32GB內存),100-120GB(128GB內存)。
innodb_log_file_size:這是redo日誌的大小。redo日誌被用於確保寫操做快速而可靠而且在崩潰時恢復。一直到MySQL 5.1,它都難於調整,由於一方面你想讓它更大來提升性能,另外一方面你想讓它更小來使得崩潰後更快恢復。幸運的是從MySQL 5.5以後,崩潰恢復的性能的到了很大提高,這樣你就能夠同時擁有較高的寫入性能和崩潰恢復性能了。一直到MySQL 5.5,redo日誌的總尺寸被限定在4GB(默承認以有2個log文件)。這在MySQL 5.6裏被提升。
一開始就把innodb_log_file_size設置成512M(這樣有1GB的redo日誌)會使你有充裕的寫操做空間。若是你知道你的應用程序須要頻繁的寫入數據而且你使用的時MySQL 5.6,你能夠一開始就把它這是成4G。max_connections:若是你常常看到‘Too many connections’錯誤,是由於max_connections的值過低了。這很是常見由於應用程序沒有正確的關閉數據庫鏈接,你須要比默認的151鏈接數更大的值。max_connection值被設高了(例如1000或更高)以後一個主要缺陷是當服務器運行1000個或更高的活動事務時會變的沒有響應。在應用程序裏使用鏈接池或者在MySQL裏使用進程池有助於解決這一問題。
InnoDB配置
從MySQL 5.5版本開始,InnoDB就是默認的存儲引擎而且它比任何其餘存儲引擎的使用都要多得多。那也是爲何它須要當心配置的緣由。
innodb_file_per_table:這項設置告知InnoDB是否須要將全部表的數據和索引存放在共享表空間裏 (innodb_file_per_table = OFF)或者爲每張表的數據單獨放在一個.ibd文件(innodb_file_per_table = ON)。每張表一個文件容許你在drop、truncate或者rebuild表時回收磁盤空間。這對於一些高級特性也是有必要的,好比數據壓縮。可是它不會帶來任何性能收益。你不想讓每張表一個文件的主要場景是:有很是多的表(好比10k+)。
MySQL 5.6中,這個屬性默認值是ON,所以大部分狀況下你什麼都不須要作。對於以前的版本你必需在加載數據以前將這個屬性設置爲ON,由於它只對新建立的表有影響。
innodb_flush_log_at_trx_commit:默認值爲1,表示InnoDB徹底支持ACID特性。當你的主要關注點是數據安全的時候這個值是最合適的,好比在一個主節點上。可是對於磁盤(讀寫)速度較慢的系統,它會帶來很巨大的開銷,由於每次將改變flush到redo日誌都須要額外的fsyncs。將它的值設置爲2會致使不太可靠(reliable)由於提交的事務僅僅每秒才flush一次到redo日誌,但對於一些場景是能夠接受的,好比對於主節點的備份節點這個值是能夠接受的。若是值爲0速度就更快了,但在系統崩潰時可能丟失一些數據:只適用於備份節點。
innodb_flush_method: 這項配置決定了數據和日誌寫入硬盤的方式。通常來講,若是你有硬件RAID控制器,而且其獨立緩存採用write-back機制,並有着電池斷電保護,那麼應該設置配置爲O_DIRECT;不然,大多數狀況下應將其設爲fdatasync(默認值)。sysbench是一個能夠幫助你決定這個選項的好工具。
innodb_log_buffer_size: 這項配置決定了爲還沒有執行的事務分配的緩存。其默認值(1MB)通常來講已經夠用了,可是若是你的事務中包含有二進制大對象或者大文本字段的話,這點緩存很快就會被填滿並觸發額外的I/O操做。看看Innodb_log_waits狀態變量,若是它不是0,增長innodb_log_buffer_size。
其餘設置
query_cache_size: query cache(查詢緩存)是一個衆所周知的瓶頸,甚至在併發並很少的時候也是如此。 最佳選項是將其從一開始就停用,設置query_cache_size = 0(如今MySQL 5.6的默認值)並利用其餘方法加速查詢:優化索引、增長拷貝分散負載或者啓用額外的緩存(好比memcache或redis)。若是你已經爲你的應用啓用了query cache而且尚未發現任何問題,query cache可能對你有用。這是若是你想停用它,那就得當心了。
log_bin:若是你想讓數據庫服務器充當主節點的備份節點,那麼開啓二進制日誌是必須的。若是這麼作了以後,還別忘了設置server_id爲一個惟一的值。就算只有一個服務器,若是你想作基於時間點的數據恢復,這(開啓二進制日誌)也是頗有用的:從你最近的備份中恢復(全量備份),並應用二進制日誌中的修改(增量備份)。二進制日誌一旦建立就將永久保存。因此若是你不想讓磁盤空間耗盡,你能夠用 PURGE BINARY LOGS 來清除舊文件,或者設置 expire_logs_days 來指定過多少天日誌將被自動清除。
記錄二進制日誌不是沒有開銷的,因此若是你在一個非主節點的複製節點上不須要它的話,那麼建議關閉這個選項。
skip_name_resolve:當客戶端鏈接數據庫服務器時,服務器會進行主機名解析,而且當DNS很慢時,創建鏈接也會很慢。所以建議在啓動服務器時關閉skip_name_resolve選項而不進行DNS查找。惟一的侷限是以後GRANT語句中只能使用IP地址了,所以在添加這項設置到一個已有系統中必須格外當心。
I 硬件配置優化
Ø CPU選擇:多核的CPU,主頻高的CPU
Ø 內存:更大的內存
Ø 磁盤選擇:更快的轉速、RAID、陣列卡,
Ø 網絡環境選擇:儘可能部署在局域網、SCI、光纜、千兆網、雙網線提供冗餘、0.0.0.0多端口綁定監聽
II操做系統級優化
Ø 使用64位的操做系統,更好的使用大內存。
Ø 設置noatime,nodiratime
Ø 優化內核參數
Ø 加大文件描述符限制
Ø 文件系統選擇 xfs
III Mysql設計優化
III.1 存儲引擎的選擇
Ø Myisam:數據庫併發不大,讀多寫少,並且都能很好的用到索引,sql語句比較簡單的應用,TB數據倉庫
Ø Innodb:併發訪問大,寫操做比較多,有外鍵、事務等需求的應用,系統內存較大。
III.2 命名規則
Ø 多數開發語言命名規則:好比MyAdress
Ø 多數開源思想命名規則:my_address
Ø 避免隨便命名
III.3 字段類型選擇
字段類型的選擇的通常原則:
Ø 根據需求選擇合適的字段類型,在知足需求的狀況下字段類型儘量小。
Ø 只分配知足需求的最小字符數,不要太慷慨。 緣由:更小的字段類型更小的字符數佔用更少的內存,佔用更少的磁盤空間,佔用更少的磁盤IO,以及佔用更少的帶寬。
對於varchar和char的選擇要根據引擎和具體狀況的不一樣來選擇,主要依據以下原則:
1.若是列數據項的大小一致或者相差不大,則使用char。
2.若是列數據項的大小差別至關大,則使用varchar。
3.對於MyISAM表,儘可能使用Char,對於那些常常須要修改而容易造成碎片的myisam和isam數據表就更是如此,它的缺點就是佔用磁盤空間。
4.對於InnoDB表,由於它的數據行內部存儲格式對固定長度的數據行和可變長度的數據行不加區分(全部數據行共用一個表頭部分,這個標頭部分存放着指向各有關數據列的指針),因此使用char類型不見得會比使用varchar類型好。事實上,由於char類型一般要比varchar類型佔用更多的空間,因此從減小空間佔用量和減小磁盤i/o的角度,使用varchar類型反而更有利。
5.表中只要存在一個varchar類型的字段,那麼全部的char字段都會自動變成varchar類型,所以建議定長和變長的數據分開。
III.4 編碼選擇
單字節 latin1
多字節 utf8(漢字佔3個字節,英文字母佔用一個字節)若是含有中文字符的話最好都統一採用utf8類型,避免亂碼的狀況發生。
III.5 主鍵選擇原則
注:這裏說的主鍵設計主要是針對INNODB引擎
1.能惟一的表示行。
2.顯式的定義一個數值類型自增字段的主鍵,這個字段能夠僅用於作主鍵,不作其餘用途。
3.MySQL主鍵應該是單列的,以便提升鏈接和篩選操做的效率。
4.主鍵字段類型儘量小,能用SMALLINT就不用INT,能用INT就不用BIGINT。
5.儘可能保證不對主鍵字段進行更新修改,防止主鍵字段發生變化,引起數據存儲碎片,下降IO性能。
6.MySQL主鍵不該包含動態變化的數據,如時間戳、建立時間列、修改時間列等。
7.MySQL主鍵應當有計算機自動生成。
8.主鍵字段放在數據表的第一順序。
推薦採用數值類型作主鍵並採用auto_increment屬性讓其自動增加。
III.6 其餘須要注意的地方
Ø NULL OR NOT NULL
儘量設置每一個字段爲NOT NULL,除非有特殊的需求,緣由以下:
1.使用含有NULL列作索引的話會佔用更多的磁盤空間,由於索引NULL列須要而外的空間來保存。
2.進行比較的時候,程序會更復雜。
3.含有NULL的列比較特殊,SQL難優化,若是是一個組合索引,那麼這個NULL 類型的字段會極大影響整個索引的效率。
Ø 索引
索引的優勢:極大地加速了查詢,減小掃描和鎖定的數據行數。
索引的缺點:佔用磁盤空間,減慢了數據更新速度,增長了磁盤IO。
添加索引有以下原則:
1 選擇惟一性索引。
2.爲常常須要排序、分組和聯合操做的字段創建索引。
3.爲常做爲查詢條件的字段創建索引。
4.限制索引的數據,索引不是越多越好。
5.儘可能使用數據量少的索引,對於大字段能夠考慮前綴索引。
6.刪除再也不使用或者不多使用的索引。
7.結合核心SQL優先考慮覆蓋索引。
8.忌用字符串作主鍵。
Ø 反範式設計
適當的使用冗餘的反範式設計,以空間換時間有的時候會很高效。
IV Mysql軟件優化
Ø 開啓mysql複製,實現讀寫分離、負載均衡,將讀的負載分攤到多個從服務器上,提升服務器的處理能力。
Ø 使用推薦的GA版本,提高性能
Ø 利用分區新功能進行大數據的數據拆分
V Mysql配置優化
注意:全局參數一經設置,隨服務器啓動預佔用資源。
Ø key_buffer_size參數
mysql索引緩衝,若是是採用myisam的話要重點設置這個參數,根據(key_reads/key_read_requests)判斷
Ø innodb_buffer_pool_size參數
INNODB 數據、索引、日誌緩衝最重要的引擎參數,根據(hit riatos和FILE I/O)判斷
Ø wait_time_out參數
線程鏈接的超時時間,儘可能不要設置很大,推薦10s
Ø max_connections參數
服務器容許的最大鏈接數,儘可能不要設置太大,由於設置太大的話容易致使內存溢出
Ø thread_concurrency參數
線程併發利用數量,(cpu+disk)*2,根據(os中顯示的請求隊列和tickets)判斷
Ø sort_buffer_size參數
得到更快的–ORDER BY,GROUP BY,SELECT DISTINCT,UNION DISTINCT
Ø read_rnd_buffer_size參數
當根據鍵進行分類操做時得到更快的–ORDER BY
Ø join_buffer_size參數
join鏈接使用全表掃描鏈接的緩衝大小,根據select_full_join判斷
Ø read_buffer_size參數
全表掃描時爲查詢預留的緩衝大小,根據select_scan判斷
Ø tmp_table_size參數
臨時內存表的設置,若是超過設置就會轉化成磁盤表,根據參數(created_tmp_disk_tables)判斷
Ø innodb_log_file_size參數(默認5M)
記錄INNODB引擎的redo log文件,設置較大的值意味着較長的恢復時間。
Ø innodb_flush_method參數(默認fdatasync)
Linux系統能夠使用O_DIRECT處理數據文件,避免OS級別的cache,O_DIRECT模式提升數據文件和日誌文件的IO提交性能
Ø innodb_flush_log_at_trx_commit(默認1)
1.0表示每秒進行一次log寫入cache,並flush log到磁盤。
2.1表示在每次事務提交後執行log寫入cache,並flush log到磁盤。
3.2表示在每次事務提交後,執行log數據寫入到cache,每秒執行一次flush log到磁盤。
VI Mysql語句級優化
1.性能查的讀語句,在innodb中統計行數,建議另外弄一張統計表,採用myisam,按期作統計.通常的對統計的數據不會要求太精準的狀況下適用。
2.儘可能不要在數據庫中作運算。
3.避免負向查詢和%前綴模糊查詢。
4.不在索引列作運算或者使用函數。
5.不要在生產環境程序中使用select * from 的形式查詢數據。只查詢須要使用的列。
6.查詢儘量使用limit減小返回的行數,減小數據傳輸時間和帶寬浪費。
7.where子句儘量對查詢列使用函數,由於對查詢列使用函數用不到索引。
8.避免隱式類型轉換,例如字符型必定要用’’,數字型必定不要使用’’。
9.全部的SQL關鍵詞用大寫,養成良好的習慣,避免SQL語句重複編譯形成系統資源的浪費。
10.聯表查詢的時候,記得把小結果集放在前面,遵循小結果集驅動大結果集的原則。
11.開啓慢查詢,按期用explain優化慢查詢中的SQL語句。
1、備份的目的
作災難恢復:對損壞的數據進行恢復和還原
需求改變:因需求改變而須要把數據還原到改變之前
測試:測試新功能是否可用
2、備份須要考慮的問題
能夠容忍丟失多長時間的數據;
恢復數據要在多長時間內完;
恢復的時候是否須要持續提供服務;
恢復的對象,是整個庫,多個表,仍是單個庫,單個表。
3、備份的類型
一、根據是否須要數據庫離線
冷備(cold backup):須要關mysql服務,讀寫請求均不容許狀態下進行;
溫備(warm backup): 服務在線,但僅支持讀請求,不容許寫請求;
熱備(hot backup):備份的同時,業務不受影響。
注:
一、這種類型的備份,取決於業務的需求,而不是備份工具
二、MyISAM不支持熱備,InnoDB支持熱備,可是須要專門的工具
二、根據要備份的數據集合的範圍
徹底備份:full backup,備份所有字符集。
增量備份: incremental backup 上次徹底備份或增量備份以來改變了的數據,不能單獨使用,要藉助徹底備份,備份的頻率取決於數據的更新頻率。
差別備份:differential backup 上次徹底備份以來改變了的數據。
建議的恢復策略:
徹底+增量+二進制日誌
徹底+差別+二進制日誌
三、根據備份數據或文件
物理備份:直接備份數據文件
優勢:備份和恢復操做都比較簡單,可以跨mysql的版本,恢復速度快,屬於文件系統級別的
建議:不要假設備份必定可用,要測試mysql>check tables;檢測表是否可用
邏輯備份: 備份表中的數據和代碼
優勢:恢復簡單、備份的結果爲ASCII文件,能夠編輯與存儲引擎無關能夠經過網絡備份和恢復
缺點:備份或恢復都須要mysql服務器進程參與備份結果佔據更多的空間,浮點數可能會丟失精度 還原以後,縮影須要重建
四:備份的對象
一、 數據;
二、配置文件;
三、代碼:存儲過程、存儲函數、觸發器
四、os相關的配置文件
五、複製相關的配置
六、二進制日誌
5、備份和恢復的實現
一、利用select into outfile實現數據的備份與還原。
二、利用mysqldump工具對數據進行備份和還原
三、利用lvm快照實現幾乎熱備的數據備份與恢復
四、基於Xtrabackup作備份恢復。
優點:
一、快速可靠的進行徹底備份
二、在備份的過程當中不會影響到事務
三、支持數據流、網絡傳輸、壓縮,因此它能夠有效的節約磁盤資源和網絡帶寬。
四、能夠自動備份校驗數據的可用性。
1、建立用戶:
CREATE USER用於建立新的MySQL帳戶。要使用CREATE USER,您必須擁有mysql數據庫的全局CREATE USER權限,或擁有INSERT權限。對於每一個帳戶,CREATE USER會在沒有權限的mysql.user表中建立一個新記錄。若是帳戶已經存在,則出現錯誤。
使用自選的IDENTIFIED BY子句,能夠爲帳戶給定一個密碼。user值和 密碼的給定方法和GRANT語句一 樣。特別是,要在純文本中指定密碼,需忽略PASSWORD關鍵詞。要把 密碼指定爲由PASSWORD()函數返回的混編值,需包含關鍵字PASSWORD
The create user command:mysql> CREATE USER yy IDENTIFIED BY ‘123’;
面創建的用戶能夠在任何地方登錄。
mysql> CREATE USER yy@localhost IDENTIFIED BY ‘123’;
2、受權:
命令:GRANT privileges ON databasename.tablename TO ‘username’@’host’
說明: privileges - 用戶的操做權限,如SELECT , INSERT , UPDATE 等.若是要授予所的權限則使
用 ALL.;databasename - 數據庫名,tablename-表名,若是要授予該用戶對全部數據庫和表的相應操
做權限則可用表示, 如.*.
GRANT SELECT, INSERT ON test.user TO ‘pig’@’%’;
GRANT ALL ON . TO ‘pig’@’%’;
注意:用以上命令受權的用戶不能給其它用戶受權,若是想讓該用戶能夠受權,用如下命令:
GRANT privileges ON databasename.tablename TO ‘username’@’host’ WITH GRANT OPTION;
刷新系統權限表
flush privileges;
3、設置與更改用戶密碼
命令:SET PASSWORD FOR ‘username’@’host’ = PASSWORD(‘newpassword’);若是是當前登錄用戶用SET PASSWORD = PASSWORD(「newpassword」);
例子:SET PASSWORD FOR ‘pig’@’%’ = PASSWORD(「123456」);
或:update mysql.user set password=password(‘新密碼’) where User=」phplamp」 and Host=」localhost」;
4、撤銷用戶權限
命令: REVOKE privilege ON databasename.tablename FROM ‘username’@’host’;
說明: privilege, databasename, tablename - 同受權部分.
例子: REVOKE SELECT ON . FROM ‘pig’@’%’;
注意: 假如你在給用戶’pig’@’%’受權的時候是這樣的(或相似的):GRANT SELECT ON test.user TO ‘pig’@’%’, 則在使用 REVOKE SELECT ON . FROM ‘pig’@’%’;命令並不能撤銷該用戶對test數據庫中user表的SELECT 操做.相反,若是受權使用的是GRANT SELECT ON . TO ‘pig’@’%’;則REVOKE SELECT ON test.user FROM ‘pig’@’%’;命令也不能撤銷該用戶對test數據庫中user表的Select 權限.具體信息能夠用命令SHOW GRANTS FOR ‘pig’@’%’; 查看.
5、刪除用戶
命令: DROP USER ‘username’@’host’;
或:DELETE FROM user WHERE User=」phplamp」 and Host=」localhost」;
//刪除用戶的數據庫
mysql>drop database phplampDB;
一、安裝配置,兩臺服務器,分別安裝好MySQL。採用單向同步的方式,就是Master的數據是主的數據,而後slave主動去Master哪兒同步數據回來。兩臺服務器的配置同樣,把關鍵的配置文件拷貝一下,兩臺服務器作相同的拷貝配置文件操做。
二、配置Master服務器,要考慮咱們須要同步那個數據庫,使用那個用戶同步,咱們這裏爲了簡單起見,就使用root用戶進行同步,而且只須要同步數據庫abc。
三、配置Slave服務器,咱們的slave服務器主要是主動去Master服務器同步數據回來。
四、測試安裝,首先查看一下slave的主機日誌:檢查是否鏈接正常, 在Master查看信息,查看Master狀態:查看Master下MySQL進程信息:在slave上查看信息:查看slave狀態:查看slave下MySQL進程信息:再在Master的abc庫裏創建表結構而且插入數據,而後檢查slave有沒有同步這些數據,就可以檢查出是否設置成功。
查看MYSQL數據庫中全部用戶
SELECT DISTINCT CONCAT(‘User: 」’,user,」’@」’,host,」’;’) AS query FROM mysql.user;
查看數據庫中具體某個用戶的權限
show grants for ‘cactiuser’@’%’;
多數狀況下,能夠認爲若是一個資源被鎖定,它總會在之後某個時間被釋放。而死鎖發生在當多個進程訪問同一數據庫時,其中每一個進程擁有的鎖都是其餘進程所需的,由此形成每一個進程都沒法繼續下去。簡單的說,進程A等待進程B釋放他的資源,B又等待A釋放他的資源,這樣就互相等待就造成死鎖。
雖然進程在運行過程當中,可能發生死鎖,但死鎖的發生也必須具有必定的條件,死鎖的發生必須具有如下四個必要條件。
1)互斥條件:指進程對所分配到的資源進行排它性使用,即在一段時間內某資源只由一個進程佔用。若是此時還有其它進程請求資源,則請求者只能等待,直至佔有資源的進程用畢釋放。
2)請求和保持條件:指進程已經保持至少一個資源,但又提出了新的資源請求,而該資源已被其它進程佔有,此時請求進程阻塞,但又對本身已得到的其它資源保持不放。
3)不剝奪條件:指進程已得到的資源,在未使用完以前,不能被剝奪,只能在使用完時由本身釋放。
4)環路等待條件:指在發生死鎖時,必然存在一個進程——資源的環形鏈,即進程集合{P0,P1,P2,•••,Pn}中的P0正在等待一個P1佔用的資源;P1正在等待P2佔用的資源,……,Pn正在等待已被P0佔用的資源。
下列方法有助於最大限度地下降死鎖:
(1)按同一順序訪問對象。
(2)避免事務中的用戶交互。
(3)保持事務簡短並在一個批處理中。
(4)使用低隔離級別。
(5)使用綁定鏈接。
實現數據庫安全性控制的經常使用方法和技術有:用戶標識和鑑別;存取控制;視圖機制;審計;數據加密;
Union由於要進行重複值掃描,因此效率低。若是合併無刻意要刪除重複行,那麼就使用Union All兩個要聯合的SQL語句 字段個數必須同樣,並且字段類型要「相容」(一致);
union和union all的區別是,union會自動壓縮多個結果集合中的重複結果,而union all則將全部的結果所有顯示出來,無論是否是重複。
Union:對兩個結果集進行並集操做,不包括重複行,同時進行默認規則的排序;
Union All:對兩個結果集進行並集操做,包括重複行,不進行排序;
Intersect:對兩個結果集進行交集操做,不包括重複行,同時進行默認規則的排序;
Minus:對兩個結果集進行差操做,不包括重複行,同時進行默認規則的排序。
能夠在最後一個結果集中指定Order by子句改變排序方式。
mysqldump -hhostname -uusername -ppassword databasename > backupfile.sql
備份MySQL數據庫爲帶刪除表的格式
備份MySQL數據庫爲帶刪除表的格式,可以讓該備份覆蓋已有數據庫而不須要手動刪除原有數據庫。
mysqldump -–add-drop-table -uusername -ppassword databasename > backupfile.sql
直接將MySQL數據庫壓縮備份
mysqldump -hhostname -uusername -ppassword databasename | gzip > backupfile.sql.gz
備份MySQL數據庫某個(些)表
mysqldump -hhostname -uusername -ppassword databasename specific_table1 specific_table2 > backupfile.sql
同時備份多個MySQL數據庫
mysqldump -hhostname -uusername -ppassword –databases databasename1 databasename2 databasename3 > multibackupfile.sql
僅僅備份數據庫結構
mysqldump –no-data –databases databasename1 databasename2 databasename3 > structurebackupfile.sql
備份服務器上全部數據庫
mysqldump –all-databases > allbackupfile.sql
還原MySQL數據庫的命令
mysql -hhostname -uusername -ppassword databasename < backupfile.sql
還原壓縮的MySQL數據庫
gunzip < backupfile.sql.gz | mysql -uusername -ppassword databasename
將數據庫轉移到新服務器
mysqldump -uusername -ppassword databasename | mysql –host=... -C databasename
第一步 檢查系統的狀態
經過操做系統的一些工具檢查系統的狀態,好比CPU、內存、交換、磁盤的利用率,根據經驗或與系統正常時的狀態相比對,有時系統表面上看起來看空閒,這也可能不是一個正常的狀態,由於cpu可能正等待IO的完成。除此以外,還應觀注那些佔用系統資源(cpu、內存)的進程。
1.1 使用sar來檢查操做系統是否存在IO問題
1.2 使用vmstat監控內存 cpu資源
1.3 磁盤IO問題,處理方式:作raid10提升性能
1.4 網絡問題,telnet一下MySQL對外開放的端口,若是不通的話,看看防火牆是否正確設置了。另外,看看MySQL是否是開啓了skip-networking的選項,若是開啓請關閉。
第二步 檢查mysql參數
2.1 max_connect_errors
2.2 connect_timeout
2.3 skip-name-resolve
2.4 slave-net-timeout=seconds
2.5 master-connect-retry
第三步 檢查mysql 相關狀態值
3.1 關注鏈接數
3.2 關注下系統鎖狀況
3.3 關注慢查詢(slow query)日誌
1.導出整個數據庫
mysqldump -u用戶名 -p密碼 數據庫名 > 導出的文件名
C:\Users\jack> mysqldump -uroot -pmysql sva_rec > e:\sva_rec.sql
2.導出一個表,包括表結構和數據
mysqldump -u用戶名 -p 密碼 數據庫名 表名> 導出的文件名
C:\Users\jack> mysqldump -uroot -pmysql sva_rec date_rec_drv> e:\date_rec_drv.sql
3.導出一個數據庫結構
C:\Users\jack> mysqldump -uroot -pmysql -d sva_rec > e:\sva_rec.sql
4.導出一個表,只有表結構
mysqldump -u用戶名 -p 密碼 -d數據庫名 表名> 導出的文件名
C:\Users\jack> mysqldump -uroot -pmysql -d sva_rec date_rec_drv> e:\date_rec_drv.sql
5.導入數據庫
經常使用source 命令
進入mysql數據庫控制檯,
如mysql -u root -p
mysql>use 數據庫
而後使用source命令,後面參數爲腳本文件(如這裏用到的.sql)
mysql>source d:wcnc_db.sql
輸入show processlist;
若是有SUPER權限,則能夠看到所有的線程,不然,只能看到本身發起的線程(這是指,當前對應的MySQL賬戶運行的線程)。
1、MySQL 鏈接本地數據庫,用戶名爲「root」,密碼「123」(注意:「-p」和「123」 之間不能有空格)
C:>mysql -h localhost -u root -p123
2、MySQL 鏈接遠程數據庫(192.168.0.201),端口「3306」,用戶名爲「root」,密碼「123」
C:>mysql -h 192.168.0.201 -P 3306 -u root -p123
MySQL 複製基於主服務器在二進制日誌中跟蹤全部對數據庫的更改(更新、刪除等等)。每一個從服務器從主服務器接收主服務器已經記錄到其二進制日誌的保存的更新,以便從服務器能夠對其數據拷貝執行相同的更新。
一、徹底備份,這是大多數人經常使用的方式,它能夠備份整個數據庫,包含用戶表、系統表、索引、視圖和存儲過程等全部數據庫對象。但它須要花費更多的時間和空間,因此,通常推薦一週作一次徹底備份。
二、事務日誌備份,事務日誌是一個單獨的文件,它記錄數據庫的改變,備份的時候只須要複製自上次備份以來對數據庫所作的改變,因此只須要不多的時間。爲了使數據庫具備魯棒性,推薦每小時甚至更頻繁的備份事務日誌。
三、差別備份也叫增量備份。它是隻備份數據庫一部分的另外一種方法,它不使用事務日誌,相反,它使用整個數據庫的一種新映象。它比最初的徹底備份小,由於它只包含自上次徹底備份以來所改變的數據庫。它的優勢是存儲和恢復速度快。推薦天天作一次差別備份。
四、文件備份,數據庫能夠由硬盤上的許多文件構成。若是這個數據庫很是大,而且一個晚上也不能將它備份完,那麼能夠使用文件備份每晚備份數據庫的一部分。因爲通常狀況下數據庫不會大到必須使用多個文件存儲,因此這種備份不是很經常使用。
查看mysql的存儲引擎:show plugins;
如何在mysql某個表中隨機抽取10條記錄
1.經過MYSQL內置的函數來操做,具體SQL代碼以下:
SELECT * FROM tablename ORDER BY RAND() LIMIT 10
2.不要將大量的工做給數據庫去作,這樣會致使數據庫在某一集中併發時間內鎖死並阻塞。建議經過PHP隨機生成一下1-X(總行數)之間的數字,而後將這10個隨機數字做爲查詢條件,具體語句如:
SELECT * FROM tablename where ID in (2,8,4,11,12,9,3,1,33)
可能你還要進行重複排除,而且須要在程序中將10個值串聯並鏈接進入SQL語句中。
show full processlist,在user字段中查看有哪些用戶
方法一: (適用於管理員或者有全局權限的用戶重設其它用戶的密碼)
進入命令行模式
mysql -u root -p
mysql>use mysql;
mysql> UPDATE user SET password=PASSWORD(「new password」) WHERE user=’username’;
mysql> FLUSH PRIVILEGES;
mysql> quit;
方法二:
mysql -u root -p
mysql>use mysql;
mysql> SET PASSWORD FOR username=PASSWORD(‘new password’);
mysql> QUIT
方法三:
mysqladmin -u root 「old password」 「new password」
注:new password請輸入你想要設置的密碼。
有兩種方法,一種方法使用mysql的check table和repair table 的sql語句,另外一種方法是使用MySQL提供的多個myisamchk, isamchk數據檢測恢復工具。
1.數據庫的設計:儘可能把數據庫設計的更小的佔磁盤空間.
1) 儘量使用更小的整數類型.(mediumint就比int更合適).
2) 儘量的定義字段爲not null,除非這個字段須要null.
3) 若是沒有用到變長字段的話好比varchar,那就採用固定大小的紀錄格式好比char.
4) 表的主索引應該儘量的短.這樣的話每條紀錄都有名字標誌且更高效.
5) 只建立確實須要的索引。索引有利於檢索記錄,可是不利於快速保存記錄。若是老是要在表的組合字段上作搜索,那麼就在這些字段上建立索引。索引的第一部分必須是最常使用的字段.若是老是須要用到不少字段,首先就應該多複製這些字段,使索引更好的壓縮。
6) 全部數據都得在保存到數據庫前進行處理。
7) 全部字段都得有默認值。
8) 在某些狀況下,把一個頻繁掃描的表分紅兩個速度會快好多。在對動態格式表掃描以取得相關記錄時,它可能使用更小的靜態格式表的狀況下更是如此。
2.系統的用途
1) 儘可能使用長鏈接.
2) explain複雜的SQL語句。
3) 若是兩個關聯表要作比較話,作比較的字段必須類型和長度都一致.
4) LIMIT語句儘可能要跟order by或者 distinct.這樣能夠避免作一次full table scan.
5) 若是想要清空表的全部紀錄,建議用truncate table tablename而不是delete from tablename.
6) 能使用STORE PROCEDURE 或者 USER FUNCTION的時候.
7) 在一條insert語句中採用多重紀錄插入格式.並且使用load data infile來導入大量數據,這比單純的insert快好多.
8) 常常OPTIMIZE TABLE 來整理碎片.
9) 還有就是date 類型的數據若是頻繁要作比較的話儘可能保存在unsigned int 類型比較快。
3.系統的瓶頸
1) 磁盤搜索。並行搜索,把數據分開存放到多個磁盤中,這樣能加快搜索時間.
2) 磁盤讀寫(IO)。能夠從多個媒介中並行的讀取數據。
3) CPU週期。數據存放在主內存中.這樣就得增長CPU的個數來處理這些數據。
4) 內存帶寬。當CPU要將更多的數據存放到CPU的緩存中來的話,內存的帶寬就成了瓶頸.
mysql> show engines; 顯示了可用的數據庫引擎的所有名單以及在當前的數據庫服務器中是否支持這些引擎。
VARCHAR和CHAR類型,varchar是變長的,須要額外的1-2個字節存儲,能節約空間,可能會對性能有幫助。但因爲是變長,可能發生碎片,如更新數據;
使用ENUM代替字符串類型,數據實際存儲爲整型。
字符串類型
要儘量地避免使用字符串來作標識符,由於它們佔用了不少空間而且一般比整數類型要慢。特別注意不要在MYISAM表上使用字符串標識符。MYISAM默認狀況下爲字符串使用了壓縮索引(Packed Index),這使查找更爲緩慢。據測試,使用了壓縮索引的MYISAM表性能要慢6倍。
還要特別注意徹底‘隨機’的字符串,例如由MD5()、SHA1()、UUID()產生的。它們產生的每個新值都會被任意地保存在很大的空間範圍內,這會減慢INSERT及一些SELECT查詢。
1)它們會減慢INSERT查詢,由於插入的值會被隨機地放入索引中。這會致使分頁、隨機磁盤訪問及彙集存儲引擎上的彙集索引碎片。
2)它們會減慢SELECT查詢,由於邏輯上相鄰的行會分佈在磁盤和內存中的各個地方。
3)隨機值致使緩存對全部類型的查詢性能都不好,由於它們會使緩存賴以工做的訪問局部性失效。若是整個數據集都變得一樣「熱」的時候,那麼把特定部分的數據緩存到內存中就沒有任何的優點了。而且若是工做集不能被裝入內存中,緩存就會進行不少刷寫的工做,而且會致使不少緩存未命中。
若是保存UUID值,就應該移除其中的短橫線,更好的辦法是使用UHEX()把UUID值轉化爲16字節的數字,並把它保存在BINARY(16)列中。
330六、1521
(1)有多少種日誌 錯誤日誌:記錄出錯信息,也記錄一些警告信息或者正確的信息 慢查詢日誌:設置一個閾值,將運行時間超過該值的全部SQL語句都記錄到慢查詢的日誌文件中。 二進制日誌:記錄對數據庫執行更改的全部操做 查詢日誌:記錄全部對數據庫請求的信息,不論這些請求是否獲得了正確的執行。 (2)日誌的存放形式 (3)事務是如何經過日誌來實現的,說得越深刻越好。 在Innodb存儲引擎中,事務日誌是經過redo和innodb的存儲引擎日誌緩衝(Innodb log buffer)來實現 的,當開始一個事務的時候,會記錄該事務的lsn(log sequence number)號; 當事務執行時,會往InnoDB存 儲引擎的日誌的日誌緩存裏面插入事務日誌;當事務提交時,必須將存儲引擎的日誌緩衝寫入磁盤(經過 innodb_flush_log_at_trx_commit來控制),也就是寫數據前,須要先寫日誌。這種方式稱爲「預寫日誌方 式」, innodb經過此方式來保證事務的完整性。也就意味着磁盤上存儲的數據頁和內存緩衝池上面的頁是不一樣步 的,是先寫入redo log,而後寫入data file,所以是一種異步的方式。 隔離性: 經過鎖實現 原子性、一致性和持久性是經過redo和undo來完成的。