不要抱怨,抱我。
MySql底层原理学习链接
MySql简介
MySQL 是一种开源的关系型数据库管理系统(RDBMS),它使用结构化查询语言(SQL)进行数据存储和管理。MySQL 是由 MySQL AB 开发的,后来被 Sun Microsystems(现为 Oracle Corporation)收购。由于其高效性、稳定性和广泛的社区支持,MySQL 已经成为世界上最流行的数据库之一。
1
git clone https://github.com/geekhournet/mysql-course //一份sql文件包,可以用来实操
ps:这个玩意学起来和shell脚本似的,各种嵌套各种关键字还有正则表达式,很简单,巨容易学,也巨容易忘。
Linux安装MySQL8.0和基础命令
安装命令
1
sudo apt install mysql-server
配置安全设置
1
sudo mysql_secure_installation
检查MySQL是否正常工作
1
systemctl status mysql
连接MySQL
1
sudo mysql -u root -p
看到mysql提示符说明连接成功了。
MySQL查看自带的数据库
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
mysql> show schemas;
+--------------------+
| Database |
+--------------------+
| information_schema |
| mysql |
| performance_schema |
| sys |
+--------------------+
4 rows in set (0.00 sec)
mysql> show databases;
+--------------------+
| Database |
+--------------------+
| information_schema |
| mysql |
| performance_schema |
| sys |
+--------------------+
4 rows in set (0.00 sec)
退出
1
mysql>quit;
更新权限
1
mysql>flush priviledges;
MySQL地址权限
很多时候数据库服务是独立安装在远程服务器上的,为了方便,一般会使用可视化客户端工具连接到远程服务器,但常常会连接失败。为了连接成功,一般会进行一些配置。
显示端口
1
2
3
4
5
6
7
8
9
10
11
12
mysql> show variables like '%port';
+--------------------------+-------+
| Variable_name | Value |
+--------------------------+-------+
| admin_port | 33062 |
| large_files_support | ON |
| mysqlx_port | 33060 |
| port | 3306 |
| report_port | 3306 |
| require_secure_transport | OFF |
+--------------------------+-------+
6 rows in set (0.02 sec)
查看和更改访问权限
1
2
3
4
5
6
7
8
9
mysql> use mysql; //选择一个数据库,一般来说下载完MySQL会自动创建一个mysql数据库,可以直接use
select user,host from user where user='root';//查看权限,如果host字段是localhost,表示这个用户只能在本地访问
+------+-----------+
| user | host |
+------+-----------+
| root | localhost |
+------+-----------+
update user set host='%' where user='root'; //将host字段改为%,就可以在任何地方访问了。(会带来安全风险)
MySQL的使用
创建和删除数据库
首先登入数据库:
1
2
sudo mysql -u root -p //登入
mysql>show databases; //查看已经存在的数据库
使用CREATE语句创建数据库:
1
2
3
4
5
6
7
8
9
10
11
12
13
mysql> create database game; //创建game数据库
mysql> show databases; //再查看一下,发现game数据库已经创建完成。
+--------------------+
| Database |
+--------------------+
| game |
| information_schema |
| mysql |
| performance_schema |
| sys |
+--------------------+
5 rows in set (0.00 sec)
使用DROP语句删除数据库:
1
2
3
4
5
6
7
8
9
10
11
12
13
mysql> drop database game; //删除game数据库
Query OK, 0 rows affected (0.01 sec)
mysql> show databases; //再查看一下,发现game数据库已经删除完成。
+--------------------+
| Database |
+--------------------+
| information_schema |
| mysql |
| performance_schema |
| sys |
+--------------------+
4 rows in set (0.00 sec)
在数据库中创建表、调整表与删除表
首先使用USE语句来进入数据库:
1
2
mysql> use game; //选择数据库
Database changed
使用CREATE语句来建表,使用desc语句来查看表结构,使用show tables查看所有存在的表:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
mysql> create table player(id INT,name VARCHAR(100),level INT,exp INT,gold DECIMAL(10,2)); // create table 表名(变量名);
Query OK, 0 rows affected (0.03 sec)
mysql> DESC player; //使用desc语句查看表的结构
+-------+---------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+-------+---------------+------+-----+---------+-------+
| id | int | YES | | NULL | |
| name | varchar(100) | YES | | NULL | |
| level | int | YES | | NULL | |
| exp | int | YES | | NULL | |
| gold | decimal(10,2) | YES | | NULL | |
+-------+---------------+------+-----+---------+-------+
5 rows in set (0.00 sec)
mysql> show tables; //使用show语句查看当前数据库的所有的表
+----------------+
| Tables_in_game |
+----------------+
| player |
+----------------+
1 row in set (0.00 sec)
使用alter语句来修改表:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
mysql> ALTER TABLE player MODIFY COLUMN name VARCHAR(200); //使用MODIFY修改表的参数
Query OK, 0 rows affected (0.02 sec)
Records: 0 Duplicates: 0 Warnings: 0
mysql> ALTER TABLE player RENAME COLUMN name to nick_name; //使用RENAME修改参数名字
Query OK, 0 rows affected (0.02 sec)
Records: 0 Duplicates: 0 Warnings: 0
mysql> ALTER TABLE player ADD COLUMN last_login DATETIME; //使用ADD增加一个新的字段
Query OK, 0 rows affected (0.06 sec)
Records: 0 Duplicates: 0 Warnings: 0
mysql> desc player; //实现的效果,可以看到name已经变成了nick_name,type类型也发生了改变,且增加了一个字段
+------------+---------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+------------+---------------+------+-----+---------+-------+
| id | int | YES | | NULL | |
| nick_name | varchar(200) | YES | | NULL | |
| level | int | YES | | NULL | |
| exp | int | YES | | NULL | |
| gold | decimal(10,2) | YES | | NULL | |
| last_login | datetime | YES | | NULL | |
+------------+---------------+------+-----+---------+-------+
6 rows in set (0.00 sec)
mysql> ALTER TABLE player DROP COLUMN last_login; //使用drop删除字段
Query OK, 0 rows affected (0.06 sec)
Records: 0 Duplicates: 0 Warnings: 0
mysql> DESC player; //实现效果,字段last_login已经被删除
+-----------+---------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+-----------+---------------+------+-----+---------+-------+
| id | int | YES | | NULL | |
| nick_name | varchar(200) | YES | | NULL | |
| level | int | YES | | NULL | |
| exp | int | YES | | NULL | |
| gold | decimal(10,2) | YES | | NULL | |
+-----------+---------------+------+-----+---------+-------+
5 rows in set (0.00 sec)
使用DROP TABLE删除表:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
mysql> create table player1(id INT); //创建表player1
Query OK, 0 rows affected (0.03 sec)
mysql> show tables; //查看
+----------------+
| Tables_in_game |
+----------------+
| player |
| player1 |
+----------------+
2 rows in set (0.00 sec)
mysql> DROP TABLE player1; //使用DROP TABLE删除表
Query OK, 0 rows affected (0.02 sec)
mysql> show tables; //效果
+----------------+
| Tables_in_game |
+----------------+
| player |
+----------------+
1 row in set (0.00 sec)
表的数据操作
使用INSERT INTO插入数据:
1
2
mysql> INSERT INTO player VALUES (1,'张三',1,1,1); //插入数据,insert into后面跟表的名称,values后面跟数据值,前面是参数名,可以灵活变动
Query OK, 1 row affected (0.01 sec)
使用select语句来查看数据:
1
2
3
4
5
6
7
mysql> select * from player; //*表示查询所有,from后面跟表的名称
+------+--------+-------+------+------+
| id | name | level | exp | gold |
+------+--------+-------+------+------+
| 1 | 张三 | 1 | 1 | 1.00 |
+------+--------+-------+------+------+
1 row in set (0.00 sec)
使用INSERT INTO插入多条数据(数据之间用逗号隔开):
1
2
3
4
5
6
7
8
9
10
11
12
13
mysql> INSERT INTO player (id,name) VALUES (2,'李四'),(3,'王五'); //插入多条数据
Query OK, 2 rows affected (0.01 sec)
Records: 2 Duplicates: 0 Warnings: 0
mysql> select * from player; //查看效果
+------+--------+-------+------+------+
| id | name | level | exp | gold |
+------+--------+-------+------+------+
| 1 | 张三 | 1 | 1 | 1.00 |
| 2 | 李四 | NULL | NULL | NULL |
| 3 | 王五 | NULL | NULL | NULL |
+------+--------+-------+------+------+
3 rows in set (0.00 sec)
添加默认值:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
mysql>ALTER TABLE player MODIFY COLUMN level INT DEFAULT 1; //默认等级为1
mysql> desc player; //查看效果
+-------+---------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+-------+---------------+------+-----+---------+-------+
| id | int | YES | | NULL | |
| name | varchar(100) | YES | | NULL | |
| level | int | YES | | 1 | |
| exp | int | YES | | NULL | |
| gold | decimal(10,2) | YES | | NULL | |
+-------+---------------+------+-----+---------+-------+
5 rows in set (0.00 sec)
mysql> INSERT INTO player (id,name) VALUES (4,'赵六'); //此时插入新数据,会自动给出默认值
Query OK, 1 row affected (0.00 sec)
mysql> select * from player;
+------+--------+-------+------+------+
| id | name | level | exp | gold |
+------+--------+-------+------+------+
| 1 | 张三 | 1 | 1 | 1.00 |
| 2 | 李四 | NULL | NULL | NULL |
| 3 | 王五 | NULL | NULL | NULL |
| 4 | 赵六 | 1 | NULL | NULL |
+------+--------+-------+------+------+
4 rows in set (0.00 sec)
使用update更新数据:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
mysql> UPDATE player set level = 1 where name='李四'; //更改李四的等级为1
Query OK, 1 row affected (0.01 sec)
Rows matched: 1 Changed: 1 Warnings: 0
mysql> select * from player; //查看
+------+--------+-------+------+------+
| id | name | level | exp | gold |
+------+--------+-------+------+------+
| 1 | 张三 | 1 | 1 | 1.00 |
| 2 | 李四 | 1 | NULL | NULL |
| 3 | 王五 | NULL | NULL | NULL |
| 4 | 赵六 | 1 | NULL | NULL |
+------+--------+-------+------+------+
4 rows in set (0.00 sec)
mysql> UPDATE player set exp=0,gold=0; //更改所有人的经验和金币都为0
Query OK, 4 rows affected (0.01 sec)
Rows matched: 4 Changed: 4 Warnings: 0
mysql> select * from player;
+------+--------+-------+------+------+
| id | name | level | exp | gold |
+------+--------+-------+------+------+
| 1 | 张三 | 1 | 0 | 0.00 |
| 2 | 李四 | 1 | 0 | 0.00 |
| 3 | 王五 | NULL | 0 | 0.00 |
| 4 | 赵六 | 1 | 0 | 0.00 |
+------+--------+-------+------+------+
4 rows in set (0.00 sec)
使用delete语句来删除数据:
1
2
3
4
5
6
7
8
9
10
11
12
13
mysql> DELETE FROM player where name='王五'; //删除王五
Query OK, 1 row affected (0.00 sec)
mysql> select * from player; //效果
+------+--------+-------+------+------+
| id | name | level | exp | gold |
+------+--------+-------+------+------+
| 1 | 张三 | 1 | 0 | 0.00 |
| 2 | 李四 | 1 | 0 | 0.00 |
| 4 | 赵六 | 1 | 0 | 0.00 |
+------+--------+-------+------+------+
3 rows in set (0.00 sec)
数据库导入和导出
导出文件:
1
2
3
ryan@ubuntu:~$ sudo mysqldump -u root -p game > game.sql //导出
ls //查看目录
cat game.sql //查看文件
导入文件:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
udo mysql -u root -p game < game.sql //导入
mysql> show tables; //查看数据库game,发现多了很多table
+----------------+
| Tables_in_game |
+----------------+
| equip |
| item |
| new_player |
| npc |
| npc_other |
| player |
| ranking |
| skill |
| top10 |
+----------------+
9 rows in set (0.00 sec)
mysql> desc player; //player表也发生了许多更改
+-------+---------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+-------+---------------+------+-----+---------+-------+
| id | int | YES | | NULL | |
| name | varchar(100) | YES | | NULL | |
| sex | varchar(10) | YES | | NULL | |
| email | varchar(100) | YES | | NULL | |
| level | int | YES | | 1 | |
| exp | int | YES | | NULL | |
| gold | decimal(10,2) | YES | | NULL | |
+-------+---------------+------+-----+---------+-------+
7 rows in set (0.00 sec)
常用语句
有超级多的关键字,建议有什么需求先去网上查一下或者chatgpt
select语句变形
NOT>AND>OR,括号可以改变优先级:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
mysql> select * FROM player WHERE level >1; //
mysql> select * FROM player WHERE level > 1 AND level < 5; //
+------+-----------+------+-----------------------+-------+------+-------+
| id | name | sex | email | level | exp | gold |
+------+-----------+------+-----------------------+-------+------+-------+
| 1 | 张三 | 男 | zhangsan@gmail.com | 3 | 19 | 20.00 |
| 2 | 赵四儿 | 男 | zhaosier@geekhour.net | 4 | 22 | 26.00 |
+------+-----------+------+-----------------------+-------+------+-------+
2 rows in set (0.00 sec)
mysql> select * FROM player WHERE exp > 1 AND level < 5; //
+------+-----------+------+-----------------------+-------+------+-------+
| id | name | sex | email | level | exp | gold |
+------+-----------+------+-----------------------+-------+------+-------+
| 1 | 张三 | 男 | zhangsan@gmail.com | 3 | 19 | 20.00 |
| 2 | 赵四儿 | 男 | zhaosier@geekhour.net | 4 | 22 | 26.00 |
| 17 | 吕秀才 | 男 | lvxiucai@gmail.com | 1 | 2 | 3.00 |
| 131 | 弈星 | 男 | yixing@geekhour.net | 1 | 61 | 90.00 |
+------+-----------+------+-----------------------+-------+------+-------+
4 rows in set (0.00 sec)
mysql> select * FROM player WHERE level > 1 AND level < 5 OR exp > 1 AND exp < 5; //
+------+-----------+------+-------------------------+-------+------+-------+
| id | name | sex | email | level | exp | gold |
+------+-----------+------+-------------------------+-------+------+-------+
| 1 | 张三 | 男 | zhangsan@gmail.com | 3 | 19 | 20.00 |
| 2 | 赵四儿 | 男 | zhaosier@geekhour.net | 4 | 22 | 26.00 |
| 17 | 吕秀才 | 男 | lvxiucai@gmail.com | 1 | 2 | 3.00 |
| 19 | 佟湘玉 | 女 | tongxiangyu@163.com | 99 | 4 | 10.00 |
| 50 | 高启强 | 男 | gaoqiqiang@geekhour.net | 88 | 3 | 30.00 |
| 136 | 女娲 | 女 | nvwa@qq.com | 89 | 2 | 86.00 |
+------+-----------+------+-------------------------+-------+------+-------+
6 rows in set (0.01 sec)
mysql> select * FROM player WHERE level BETWEEN 1 AND 10; //
+------+-----------+------+-----------------------+-------+------+-------+
| id | name | sex | email | level | exp | gold |
+------+-----------+------+-----------------------+-------+------+-------+
| 1 | 张三 | 男 | zhangsan@gmail.com | 3 | 19 | 20.00 |
| 2 | 赵四儿 | 男 | zhaosier@geekhour.net | 4 | 22 | 26.00 |
| 11 | 胡一菲 | 女 | huyifei@163.com | 6 | 53 | 38.00 |
| 17 | 吕秀才 | 男 | lvxiucai@gmail.com | 1 | 2 | 3.00 |
| 31 | 周伯通 | 男 | zhoubotong@163.com | 8 | 45 | 70.00 |
| 37 | 慕容复 | 男 | murongfu@gmail.com | 5 | 49 | 38.00 |
| 49 | 安欣 | 男 | anxin@gmail.com | 8 | 43 | 33.00 |
| 87 | 小鱼儿 | 男 | xiaoyuer@163.com | 6 | 55 | 4.00 |
| 91 | 余则成 | 男 | yuzecheng@163.com | 10 | 53 | 29.00 |
| 131 | 弈星 | 男 | yixing@geekhour.net | 1 | 61 | 90.00 |
+------+-----------+------+-----------------------+-------+------+-------+
10 rows in set (0.00 sec)
like模糊查找(正则表达式)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
mysql> select * FROM player WHERE name LIKE '王%'; //%通配所有
+------+-----------+------+---------------------------+-------+------+-------+
| id | name | sex | email | level | exp | gold |
+------+-----------+------+---------------------------+-------+------+-------+
| 3 | 王五 | 女 | wangwu@163.com | 64 | 38 | 15.00 |
| 7 | 王小二 | 男 | wangxiaoer@163.com | 70 | 30 | 54.00 |
| 33 | 王重阳 | 男 | wangchongyang@gmail.com | 38 | 63 | 38.00 |
| 54 | 王语嫣 | 女 | wangyuyan@geekhour.net | 71 | 97 | 85.00 |
| 82 | 王小蒙 | 女 | wangxiaomeng@geekhour.net | 95 | 77 | 44.00 |
| 169 | 王昭君 | 女 | wangzhaojun@gmail.com | 96 | 48 | 11.00 |
+------+-----------+------+---------------------------+-------+------+-------+
6 rows in set (0.00 sec)
ysql> select * FROM player WHERE name LIKE '%王%'; //
+------+-----------+------+---------------------------+-------+------+-------+
| id | name | sex | email | level | exp | gold |
+------+-----------+------+---------------------------+-------+------+-------+
| 3 | 王五 | 女 | wangwu@163.com | 64 | 38 | 15.00 |
| 7 | 王小二 | 男 | wangxiaoer@163.com | 70 | 30 | 54.00 |
| 33 | 王重阳 | 男 | wangchongyang@gmail.com | 38 | 63 | 38.00 |
| 54 | 王语嫣 | 女 | wangyuyan@geekhour.net | 71 | 97 | 85.00 |
| 82 | 王小蒙 | 女 | wangxiaomeng@geekhour.net | 95 | 77 | 44.00 |
| 160 | 牛魔王 | 男 | niumowang@qq.com | 11 | 16 | 46.00 |
| 168 | 兰陵王 | 男 | lanlingwang@qq.com | 64 | 22 | 12.00 |
| 169 | 王昭君 | 女 | wangzhaojun@gmail.com | 96 | 48 | 11.00 |
+------+-----------+------+---------------------------+-------+------+-------+
8 rows in set (0.00 sec)
mysql> select * FROM player WHERE name LIKE '王_'; //_通配单字
+------+--------+------+----------------+-------+------+-------+
| id | name | sex | email | level | exp | gold |
+------+--------+------+----------------+-------+------+-------+
| 3 | 王五 | 女 | wangwu@163.com | 64 | 38 | 15.00 |
+------+--------+------+----------------+-------+------+-------+
1 row in set (0.00 sec)
正则表达式REGEXP:
1
2
3
4
5
6
7
mysql> select * FROM player WHERE name REGEXP '^王.$';
+------+--------+------+----------------+-------+------+-------+
| id | name | sex | email | level | exp | gold |
+------+--------+------+----------------+-------+------+-------+
| 3 | 王五 | 女 | wangwu@163.com | 64 | 38 | 15.00 |
+------+--------+------+----------------+-------+------+-------+
1 row in set (0.01 sec)
查找空值
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
mysql> select * FROM player WHERE email is null; //
+------+-----------+------+-------+-------+------+-------+
| id | name | sex | email | level | exp | gold |
+------+-----------+------+-------+-------+------+-------+
| 12 | 吕子乔 | 男 | NULL | 36 | 100 | 46.00 |
| 13 | 吕小布 | 男 | NULL | 81 | 88 | 25.00 |
+------+-----------+------+-------+-------+------+-------+
2 rows in set (0.00 sec)
mysql> select * FROM player WHERE email is NOT null; //
mysql> select * FROM player WHERE email is null OR email=''; //
+------+-----------+------+-------+-------+------+-------+
| id | name | sex | email | level | exp | gold |
+------+-----------+------+-------+-------+------+-------+
| 12 | 吕子乔 | 男 | NULL | 36 | 100 | 46.00 |
| 13 | 吕小布 | 男 | NULL | 81 | 88 | 25.00 |
| 190 | 吕布 | 男 | | 77 | 43 | 31.00 |
+------+-----------+------+-------+-------+------+-------+
3 rows in set (0.00 sec)
ORDER BY排序
1
2
3
mysql> select * FROM player ORDER BY level; //升序排序
mysql> select * FROM player ORDER BY level DESC; //降序排序
mysql> select * FROM player ORDER BY level DESC,exp ASC; //等级降序,经验升序
聚合函数(有很多,这里只列举几个)
计数函数:
1
2
3
4
5
6
7
mysql> select COUNT(*) FROM player; //计数
+----------+
| COUNT(*) |
+----------+
| 209 |
+----------+
1 row in set (0.01 sec)
均值函数:
1
2
3
4
5
6
7
mysql> select AVG(level) FROM player; //所有玩家的等级均值
+------------+
| AVG(level) |
+------------+
| 55.0813 |
+------------+
1 row in set (0.00 sec)
group by分组
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
mysql> select sex,COUNT(*) FROM player group by sex;
+------+----------+
| sex | COUNT(*) |
+------+----------+
| 男 | 140 |
| 女 | 65 |
| NULL | 3 |
| | 1 |
+------+----------+
4 rows in set (0.00 sec)
//分组后having过滤,然后降序
mysql> select level,COUNT(*) FROM player group by level having count(level)>4 order by COUNT(level) DESC;
+-------+----------+
| level | COUNT(*) |
+-------+----------+
| 13 | 9 |
| 96 | 7 |
| 95 | 5 |
| 88 | 5 |
| 54 | 5 |
+-------+----------+
5 rows in set (0.00 sec)
子查询
有的时候,我们需要使用一个查询结果作为另一个查询的条件。
1
mysql> select * from player where level > (select AVG(level) from player); //把一个查询套上括号
查询结果创建新表:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
mysql> create table new_table (select * from player where level < 5);
Query OK, 4 rows affected (0.03 sec)
Records: 4 Duplicates: 0 Warnings: 0
mysql> show tables;
+----------------+
| Tables_in_game |
+----------------+
| equip |
| item |
| new_player |
| new_table |
| npc |
| npc_other |
| player |
| ranking |
| skill |
| top10 |
+----------------+
10 rows in set (0.00 sec)
表关联
表关联用来查询多个表中的数据,关联的表必须要有相同字段。
在关系型数据库中,表关联(Join)是一种将两个或多个表的数据结合在一起的操作,通常用于根据某些条件从多个表中获取相关的数据。表关联可以基于共同的列(通常是主键与外键关系)将数据链接在一起。
内连接(INNER JOIN)
- 返回两个表中匹配的行。如果在某个表中没有匹配行,则这些行不会出现在结果中。
- 适用于你只关心两个表中存在共同数据的场景。
以装备表equip和玩家player表为例:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
mysql> select * from player
-> inner join equip
-> on player.id=equip.player_id;
+------+-----------+------+---------------------+-------+------+-------+------+-----------------+-----------+
| id | name | sex | email | level | exp | gold | id | name | player_id |
+------+-----------+------+---------------------+-------+------+-------+------+-----------------+-----------+
| 76 | 林克 | 男 | linke@qq.com | 48 | 12 | 11.00 | 6 | 大师之剑 | 76 |
| 157 | 张飞 | 男 | zhangfei@gmail.com | 76 | 36 | 80.00 | 2 | 丈八蛇矛 | 157 |
| 161 | 孙悟空 | 男 | sunwukong@gmail.com | 74 | 32 | 23.00 | 7 | 金箍棒 | 161 |
| 177 | 关羽 | 男 | guanyu@gmail.com | 19 | 60 | 36.00 | 1 | 青龙偃月刀 | 177 |
| 186 | 曹操 | 男 | caocao@geekhour.net | 70 | 15 | 27.00 | 3 | 七星宝刀 | 186 |
| 190 | 吕布 | 男 | | 77 | 43 | 31.00 | 9 | 赤兔马 | 190 |
| 190 | 吕布 | 男 | | 77 | 43 | 31.00 | 8 | 方天画戟 | 190 |
+------+-----------+------+---------------------+-------+------+-------+------+-----------------+-----------+
7 rows in set (0.01 sec)
左连接(LEFT JOIN 或 LEFT OUTER JOIN)
- 返回左表(第一个表)中的所有行以及右表(第二个表)中匹配的行。如果右表没有匹配的行,则右表的结果为空(NULL)。
- 适用于你想保留左表所有记录,无论是否在右表中找到匹配项的场景。
左连接把左表所有数据全部输出(太多了只截取一部分),右表匹配上的匹配,匹配不上的全是NULL:
1
2
3
4
5
6
7
8
9
10
mysql> select * from player left join equip on player.id=equip.player_id;
+------+--------------+------+----------------------------+-------+------+--------+------+-----------------+-----------+
| id | name | sex | email | level | exp | gold | id | name | player_id |
+------+--------------+------+----------------------------+-------+------+--------+------+-----------------+-----------+
| 1 | 张三 | 男 | zhangsan@gmail.com | 3 | 19 | 20.00 | NULL | NULL | NULL |
| 2 | 赵四儿 | 男 | zhaosier@geekhour.net | 4 | 22 | 26.00 | NULL | NULL | NULL |
| 3 | 王五 | 女 | wangwu@163.com | 64 | 38 | 15.00 | NULL | NULL | NULL |
| 4 | 刘能 | 男 | liuneng@qq.com | 30 | 95 | 1.00 | NULL | NULL | NULL |
| 5 | 范德彪 | 男 | fandebiao@gmail.com | 95 | 89 | 44.00 | NULL | NULL | NULL |
右连接(RIGHT JOIN 或 RIGHT OUTER JOIN)
- 返回右表(第二个表)中的所有行,以及左表(第一个表)中匹配的行。如果左表没有匹配的行,则左表的结果为空(NULL)。
- 适用于你想保留右表所有记录,无论是否在左表中找到匹配项的场景。
右连接把右表所有数据全部输出,左表匹配上的匹配,匹配不上的全是NULL:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
mysql> select * from player right join equip on player.id=equip.player_id;
+------+-----------+------+---------------------+-------+------+-------+------+-----------------+-----------+
| id | name | sex | email | level | exp | gold | id | name | player_id |
+------+-----------+------+---------------------+-------+------+-------+------+-----------------+-----------+
| 177 | 关羽 | 男 | guanyu@gmail.com | 19 | 60 | 36.00 | 1 | 青龙偃月刀 | 177 |
| 157 | 张飞 | 男 | zhangfei@gmail.com | 76 | 36 | 80.00 | 2 | 丈八蛇矛 | 157 |
| 186 | 曹操 | 男 | caocao@geekhour.net | 70 | 15 | 27.00 | 3 | 七星宝刀 | 186 |
| NULL | NULL | NULL | NULL | NULL | NULL | NULL | 4 | 长剑 | NULL |
| NULL | NULL | NULL | NULL | NULL | NULL | NULL | 5 | 铁盾 | NULL |
| 76 | 林克 | 男 | linke@qq.com | 48 | 12 | 11.00 | 6 | 大师之剑 | 76 |
| 161 | 孙悟空 | 男 | sunwukong@gmail.com | 74 | 32 | 23.00 | 7 | 金箍棒 | 161 |
| 190 | 吕布 | 男 | | 77 | 43 | 31.00 | 8 | 方天画戟 | 190 |
| 190 | 吕布 | 男 | | 77 | 43 | 31.00 | 9 | 赤兔马 | 190 |
+------+-----------+------+---------------------+-------+------+-------+------+-----------------+-----------+
9 rows in set (0.00 sec)
索引
在数据库管理系统中,索引(Index)是一种数据结构,用于提高数据检索速度。它通过创建一个数据项的“指针”来快速定位到数据表中的数据行,避免了对整个数据表进行全表扫描,从而显著提高查询效率。索引类似于书本的目录,帮助你快速找到某个章节或内容。
创建索引后正常查询即可。
创建普通索引:
1
CREATE INDEX index_name ON table_name (column_name);
建表时直接定义索引:
1
2
3
4
5
CREATE TABLE table_name (
id INT,
name VARCHAR(100),
INDEX (name)
);
删除索引:
1
DROP INDEX index_name ON table_name;
视图索引
在关系型数据库中,视图(View)是一个虚拟表,它是由一个或多个表的查询结果所组成的。视图本身不存储数据,而是通过查询定义来动态地生成数据(有点像shell脚本)。可以将视图视为一个“虚拟表”,你可以像操作普通表一样对视图进行查询、插入、更新和删除等操作,但视图背后存储的是查询结果而不是物理数据。
创建视图:
1
2
3
mysql> CREATE VIEW top10
-> AS
-> select * from player order by level desc limit 10;
使用视图:
1
2
3
4
5
6
7
8
9
10
11
mysql> select * from top10;
+------+-----------+------+-----------------------+-------+------+-------+
| id | name | sex | email | level | exp | gold |
+------+-----------+------+-----------------------+-------+------+-------+
| 17 | 吕秀才 | 男 | lvxiucai@gmail.com | 1 | 2 | 3.00 |
| 131 | 弈星 | 男 | yixing@geekhour.net | 1 | 61 | 90.00 |
| 1 | 张三 | 男 | zhangsan@gmail.com | 3 | 19 | 20.00 |
| 2 | 赵四儿 | 男 | zhaosier@geekhour.net | 4 | 22 | 26.00 |
| 37 | 慕容复 | 男 | murongfu@gmail.com | 5 | 49 | 38.00 |
+------+-----------+------+-----------------------+-------+------+-------+
5 rows in set (0.01 sec)