MySQL語法速查1:基礎命令篇
[TOC]
1.1. 關於 SQL
SQL 是 Structure Query Language(結構化查詢語言)的縮寫,是關係型資料庫的基本語言,由 IBM 在 20 世紀 70 年代開發出來,作為 IBM 關係資料庫原型 System R 的原型關係語言,實現了關係資料庫中的資訊檢索。
20 世紀 80 年代初,美國國家標準局(ANSI)開始著手製作 SQL 標準,並於 1986 年完成,被叫做 SQL-86。
SQL 標準幾經修改,日趨完善,大多數關係型資料庫系統都支援,而 (My)SQL 是在標準 SQL 的基礎上進行了擴充套件。
1.2. SQL 分類
- DDL(Data Definition Language):資料定義語句
- 主要用於操作資料庫物件
- 常用關鍵字 create、drop、alter等;
- 主要用於操作資料庫物件
- DML(Data Manipulation Language):資料操作語句
- 主要用於操作資料庫記錄;
- 常用關鍵字 insert、delete、update、select等;
- DCL(Data Control Language):資料控制語句
- 主要用於控制資料的訪問許可權;
- 常用關鍵字 grant、revoke等。
1.3. DDL
1.3.1. 建立資料庫
CREATE DATABASE db_name;
1.3.2. 刪除資料庫
DROP DATABASE db_name;
1.3.3. 建立表
CREATE TABLE table_name( field1_name field1_type [field1_constraints], field2_name field2_type [field2_constraints], field3_name field3_type [field3_constraints], ... [PRIMARY KEY ( field1_name ),] [INDEX `idx_field1_name`(`field1_name`) USING BTREE COMMENT '',] ... ) [table_constraints];
說明:
- field1_name 欄位名,建議以下劃線分隔單詞,如
update_at
。 - field1_type 欄位型別
- int、char、varchar、float、decimal、datatime等。
- 數值型的欄位後跟括號,用於設定欄位的顯示寬度,如
int(11)
。- 如果所插入數值的位數小於指定的寬度時會用空格填充;若同時使用
zerofill
約束,則會以 0 來填充。 - 注意:顯示寬度只用於顯示,並不能限制取值範圍和佔用空間,每種資料型別的實際取值範圍決定資料能否最終插入資料庫。
- 如果插入的值超過欄位的實際取值範圍,則提示:
1264 - Out of range value for column xxxx
- 如果所插入數值的位數小於指定的寬度時會用空格填充;若同時使用
- 字元型的欄位後跟括號,用於設定可存放值的範圍,如:
varcahr(5)
- 嚴格模式下,如果插入 6 位字串,則提示:
406 - Data too long for column xxxx
。 - 非嚴格模式下,如果插入 6 位字串,則會進行擷取後成功插入資料庫,並且顯示一個 warning。
- 嚴格模式下,如果插入 6 位字串,則提示:
- field1_constraints 欄位約束條件
NOT NULL
不允許為空,預設允許為空。AUTO_INCREMENT
設定為自增列,在 MySQL 中無論 InnoDB 引擎還是 MyISAM 引擎的表,只能有一個自增列,並且自增列一定是索引列,無論是二級索引還是主鍵索引。DEFAULT
預設值,預設 NULL。COMMENT '註釋資訊'
欄位註釋unsigned
數值型欄位無符號,預設有符合。zerofill
當所插入欄位值的長度沒有達到在欄位型別中設定的長度時,用 0 來補全。CHARACTER SET utf8mb4
設定欄位的字符集。COLLATE utf8mb4_bin
- table_constraints 表約束條件
ENGINE=InnoDB
設定表的儲存引擎,預設 InnoDB,MySQL5.x 以下預設 MyISAM。- MyISAM 支援全文字搜尋
- InnoDB 支援事務處理
- MEMORY 類似MyISAM,但資料儲存在記憶體中,速度很快(特別適合臨時表)。
DEFAULT CHARSET=utf8
設定預設字符集AUTO_INCREMENT=10
設定自增列的開始位置,查看錶中自增欄位的下一個值,使用SHOW TABLE STATUS LIKE 'table_name';
獲取欄位 Auto_increment 的值。COMMENT '註釋資訊'
表的註釋資訊
查看錶的定義
DESC table_name;
-- 或
SHOW CREATE TABLE table_name \G;
1.3.4. 刪除表
DROP TABLE table_name;
-- 刪除多張表,並且刪除之前先判斷是否存在
DROP TABLE IF EXISTS table1_name,table2_name,.....;
1.3.5. 修改表
注意 ⚠️:
關鍵字
CHANGE
和FIRST
|AFTER COLUMN
屬於 MySQL 在標準 SQL 上的擴充套件,並不一定適用於其它資料庫。field_definition 至少包含欄位名和欄位型別。
-
修改表型別
ALTER TABLE table_name MODIFY [COLUMN] field_definition [FIRST | AFTER field_name];
-
增加表字段
ALTER TABLE table_name ADD [COLUMNM] field_definition [FIRST | AFTER field_name];
-
刪除表字段
ALTER TABLE table_name DROP [COLUMN] field_name;
-
修改欄位名
ALTER TABLE table_name CHANGE [COLUMN] old_field_name field_definition [FIRST | AFTER field_name];
-
修改欄位排列順序
使用前面的可選引數
[FIRST | AFTER field_name]
,其中:- ADD 新增的欄位預設在表的最後位置;
- CHANGE 或 MODIFY 預設不改變欄位的位置。
-
更改表名
ALTER TABLE table_name RENAME [TO] new_table_name;
1.3.6. 修改表-外來鍵
-- 新增
ALTER TABLE table1 ADD CONSTRAINT fk_table1_table2 FOREIGN KEY (table1) REFERENCES table2 (id);
-- 刪除
ALTER TABLE table1 DROP FOREIGN KEY fk_table1_table2;
1.3.7. 修改表-索引
這裡只介紹了通過修改表結構的方式建立索引,此外還有其它兩種方式(CREATE INDEX
或 在 CREATE TABLE
時指定 `),詳見後續文章索引部分。
-
普通索引
-- 新增 ALTER TABLE table1 ADD INDEX idx_name(field1); -- 刪除 ALTER TABLE table1 DROP INDEX idx_name;
-
主鍵索引
-- 新增 -- 先修改要設定為主鍵的欄位:無符號、非空、自增 ALTER TABLE table1 MODIFY COLUMN `id` int(11) UNSIGNED NOT NULL AUTO_INCREMENT, ADD PRIMARY KEY (`id`); -- 刪除 ALTER TABLE table1 DROP PRIMARY KEY;
-
唯一索引
-- 新增 ALTER table mytable ADD UNIQUE [idx_name] (field1(length)) -- 刪除 ALTER TABLE table1 DROP UNIQUE field1;
-
查詢表的索引
SHOW INDEX FROM table_name;
1.4. DML
1.4.1. 新增記錄(增)
-- 插入一條
INSERT INFO table_name(field1,field2,...,fieldn) VALUES(val1,val2,...,valn);
-- 插入多條
INSERT INTO table_name(field1,field2,...,fieldn)
VALUES
(record1_val1,record1_val2,...,record1_valn),
(record2_val1,record2_val2,...,record2_valn),
...
(recordn_val1,recordn_val2,...,recordn_valn);
field1,field2,...,fieldn
可以不用寫,但是後面VALUES
裡值的順序需要與表中的欄位順序保持一致;- 如果待插入的資料,不包含以下型別的欄位,可以不用寫
- 可空:自動設定為 NULL;
- 有預設值:自動設定為預設值;
- 自增:自動設定為下一個自增值。
1.4.2. 刪除記錄(刪)
DELETE FROM table_name [WHERE condition];
-- 一次刪除多張表
DELETE t1,t2,... FROM table1 t1,table2 t2,... [WHERE condition];
1.4.3. 更新記錄(改)
UPDATE table_name SET field1=val1,field2=val2,...,fieldn=valn [WHERE condition];
-- 一次更新多個表
UPDATE table1 a,table2 b, tablen n SET a.field1=val1,...,n.fieldn=valn [WHERE condition];
1.4.4. 查詢記錄(查)
-
基本
SELECT * FROM table_name [WHERE condition] [ORDER BY field1 [DESC|ASC], field2 [DESC|ASC], ...] [LIMIT offset_start,row_count];
說明:
[WHERE condition]
過濾條件[ORDER BY field1 [DESC|ASC], field2 [DESC|ASC], ...]
排序- ASC 升序(預設)
- DESC 降序
[LIMIT offset_start,row_count]
限制
-
去重查詢
SELECT distinct field1 FROM table_name [WHERE condition];
-
聚合(彙總統計)
SELECT [field1,field2,...] func_name FROM table_name [WHERE condition] [GROUP BY field1,field2,...] [WITH ROLLUIP] [HAVING condition]
說明:
func_name
聚合函式,常用:sum 求和、count(*) 記錄數、max 最大值、min 最小值。[WHERE condition]
聚合前按條件對結果進行過濾,應儘量使用此過濾以減少待聚合的結果集,提高聚合效率。[GROUP BY field1,field2,...]
分類聚合欄位[WITH ROLLUIP]
是否對分類聚合後的結果進行再彙總。[HAVING condition]
對聚合後的結果再進行條件過濾。
-
內連線
僅獲取兩張表中互相匹配的記錄
SELECT field1,field2 FROM table1 t1,table2 t2 WHERE t1.outid=t2.outid
其中
field1,field2,...
分別儲存在兩張表中。 -
外連線
-
左連線
包含所有左邊表中的記錄,甚至是右邊表中沒有和它匹配的記錄。
SELECT field1,field2,... FROM table1 t1 LEFT JOIN table2 t2 ON t2.outid=t1.outid
-
右連線
包含所有右邊表中的記錄,甚至是右邊表中沒有和它匹配的記錄。
SELECT field1,field2,... FROM table1 t1 RIGHT JOIN table2 t2 ON t2.outid=t1.outid
-
-
子查詢
當進行查詢時,需要的條件是另一個 select 語句的結果時將用到子查詢功能。
SELECT field1,field2,... FROM table1 WHERE outid IN( SELECT outid FROM table2 );
除了 IN,用於子查詢的關鍵字還有:
NOT IN
、=
、!=
、EXISTS
、NOT EXISTS
等。MySQL4.1 以前的版本不支援子查詢,需要用表連線來實現,如:
SELECT t1.* FROM table1 t1,table2 t2 WHERE t1.outid=t2.outid
-
聯合(合併結果集)
SELECT * FROM table1 UNION | UNION ALL SELECT * FROM table2 ... UNION | UNION ALL SELECT * FROM tablen
說明:
UNION ALL
把結果集直接合並在一起。UNION
是將UNION ALL
的結果集執行一次DISTINCT
,去除重複記錄後的結果。
1.5. DCL
1.5.1. 授予許可權
GRANT select,insert ON db1.* TO 'user1'@'localhost' IDENTIFIED BY '123';
1.5.2. 收回許可權
REVOKE insert ON db1.* FROM 'user1'@'localhost';
1.6. 附錄
1.6.1. 連線資料庫
mysql [-h127.0.0.1] [-P3306] -uroot -p[password]
引數說明:
-h
可選,資料庫地址(IP或域名),預設 127.0.0.1。-P
可選,資料庫埠號,預設 3306.-u
資料庫登入使用者-p
資料庫登入使用者對應的密碼
示例:
$ mysql -uroot -p
Enter password:
Welcome to the MySQL monitor. Commands end with ; or \g.
Your MySQL connection id is 4
Server version: 5.7.24-log MySQL Community Server (GPL)
Copyright (c) 2000, 2018, Oracle and/or its affiliates. All rights reserved.
Oracle is a registered trademark of Oracle Corporation and/or its
affiliates. Other names may be trademarks of their respective
owners.
Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.
MySQL [(none)]> show databases;
+--------------------+
| Database |
+--------------------+
| information_schema |
| mysql |
| performance_schema |
| sys |
+--------------------+
4 rows in set (0.00 sec)
MySQL [(none)]> exit
Bye
1.6.2. 如何使用系統幫助
在命令列模式下,使用 ? contents
命令檢視對應分類的幫助資訊。
如:
-- 檢視 show 相關的所有命令等
mysql> ? show
1.6.3. 什麼是元資料資訊
元資料指資料的資料,比如表名、列名、列型別、索引名等表的各種屬性名稱。MySQL 5.0 之後提供來一個新的資料庫 information_schema
,用來記錄 MySQL 中的元資料資訊。
- 這是一個比較特殊的資料庫,它在物理上並不存在相關的目錄和檔案;
- 對應資料庫裡使用
show tables
顯示的各種“表”也並不是實際存在的物理表,而全部是檢視。
常用的檢視如下:
SCHEMATA
提供當前 MySQL 例項中所有的資料庫資訊,對應show databases;
的結果。TABLES
提供關於資料庫中的表資訊(包括檢視),詳細表述裡某個表屬於那個 schema、表型別、表引擎、建立時間等,對應show tables from schemaname;
的結果。COLUMNS
提供所有表中的列資訊,對應show columns from schemaname.tablename;
的結果。STATISTICS
提供關於表索引的資訊,對應show index from schemaname.tablename;
的結果。