1、连接mysql
mysql -uroot -p
mysql -uroot -p -hlocalhost -e"select user()" //查看mysql当前用户
2、sql访问控制语句
help create user;//查看create user的帮助信息
mysql> help create user;
Name: 'CREATE USER'
Description:
Syntax:
CREATE USER [IF NOT EXISTS]
user [auth_option] [, user [auth_option]] ...//用户名user@访问控制列表
DEFAULT ROLE role [, role ] ... //指定角色,特殊用户,具有某些权限
[REQUIRE {NONE | tls_option [[AND] tls_option] ...}]
[WITH resource_option [resource_option] ...]
[password_option | lock_option] ...
user:
(see )
auth_option: {
IDENTIFIED BY 'auth_string'
| IDENTIFIED WITH auth_plugin
| IDENTIFIED WITH auth_plugin BY 'auth_string'
| IDENTIFIED WITH auth_plugin AS 'hash_string'
}
tls_option: { //加密连接参数
SSL //加密协议
| X509
| CIPHER 'cipher'
| ISSUER 'issuer'
| SUBJECT 'subject'
}
resource_option: {
MAX_QUERIES_PER_HOUR count //每小时最大查询数量
| MAX_UPDATES_PER_HOUR count //每小时最大更新数量
| MAX_CONNECTIONS_PER_HOUR count //每小时最大连接数量
| MAX_USER_CONNECTIONS count //每小时最大用户连接数量
}
password_option: {
PASSWORD EXPIRE [DEFAULT | NEVER | INTERVAL N DAY]
| PASSWORD HISTORY {DEFAULT | N}
| PASSWORD REUSE INTERVAL {DEFAULT | N DAY}
| PASSWORD REQUIRE CURRENT [DEFAULT | OPTIONAL]
}
lock_option: {
ACCOUNT LOCK
| ACCOUNT UNLOCK
}
show plugins; //查看mysql支持的插件
以下3个是它支持的认证插件
mysql_native_password //mysql 5.6以前默认
sha256_password
caching_sha2_password //mysql8.0默认插件==》加入缓存,可以加快认证连接速度
创建mc_test用户,允许218.244.148.176客户端连接,最大连接数为1.
mysql> create user my_test@'218.244.148.176' identified by 'Wss1311292738.' with max_user_connections 1;
[root@izbp173bkvqwhsk998g7scz ~]# mysql -umy_test -p -h218.244.148.176
Enter password:
查看账户权限
mysql> show privileges; //50个权限
mysql> use mysql
//mysql是mysql数据库下的一个系统库,记录了mysql账户信息,主机列表,一些权限
mysql> desc user; //查看上述信息即user表
给账户授权
mysql> grant select(user,host) on mysql.user to my_test@'218.244.148.176';
//给用户my_test授予mysql.user表上的user和host列的select(查询)权限
mysql> grant select,update on mysql.user to my_test@'218.244.148.176';
//给用户my_test授予mysql.user表上的所有列的select(查询)和updete(更新)权限
mysql> grant delete,insert on mysql.* to my_test@'218.244.148.176';
//给用户my_test授予mysql.上的所有表的delete(删除),insert(插入)权限
使用grant授权的数据库账户必须存在,以下验证以下:
**用户使用grant命令授权,必须具有grant option的权限,**即就是,我要通过grant授予别人权限,我自己得先拥有该权限。
mysql> \h grant //grant帮助命令
回收用户权限
mysql> revoke select,delete on mysql.user from my_test@218.244.148.176;
//回收用户my_test在mysql中user表上的select和delete权限。
3.DDL语句
建立、修改、删除数据库:create/alter/drop database;
建立、修改、删除表:create/alter/drop table;
建立、删除索引:create/drop index;
清空表:truncate table;===>先删除表,再建空表
重命名表:rename table;
建立、修改、删除视图:create/alter/drop view;
mysql> create database imc_db; //创建数据库 imc_db
mysql> truncate table imc_db;//清空表
mysql> rename table imc_db to bak_imc_db; //重命名表
4. DML语句(操作表)
新增:insert into
删除:delete
修改:update
查询:select
(1)对表操作
//使用数据库
mysql> use imc_db;
//在库下创建表
mysql> create table imc_class (
class_id int auto_increment not null comment '课程分类id', //id自动增长且不空
class_name varchar(10) not null default '' comment '分类名称',//不空默认''
add_time timestamp not null default current_timestamp comment '添加时间',
//添加时间为timestamp类型,不空默认当前时间类型。
primary key ( class_id ) //主键
) comment '课程分类' ;
//给表插入数据
mysql> insert into imc_class (class_name) values ('mysql'),('mongodb');
//查看表
mysql> select * from imc_class;
+----------+------------+---------------------+
| class_id | class_name | add_time |
+----------+------------+---------------------+
| 1 | mysql | 2021-02-15 10:59:26 |
| 2 | mongodb | 2021-02-15 10:59:26 |
+----------+------------+---------------------+
//class_name 为业务主键,不能重复的,所以为它建立唯一索引
mysql> create unique index uqx_classname on imc_class (class_name);
//若此时再插入mysql,mongodb,就会报错
mysql> insert into imc_class (class_name) values ('mysql'),('mongodb');
ERROR 1062 (23000): Duplicate entry 'mysql' for key 'uqx_classname'
// 在唯一索引中重复输入 ‘mysql’
//如果想让重复插入的数据仅仅把添加时间更新一下。
mysql> insert into imc_class (class_name) values ('mysql') //插入'mysql'
on duplicate key update add_time=current_time; //在duplicate 重复时,add_time这个key更新为current_time。
mysql> select * from imc_class;
+----------+------------+---------------------+
| class_id | class_name | add_time |
+----------+------------+---------------------+
| 1 | mysql | 2021-02-15 11:20:01 |
| 2 | mongodb | 2021-02-15 10:59:26 |
+----------+------------+---------------------+
(2)select语句
mysql> select 'hello',2018+1;
+-------+--------+
| hello | 2018+1 |
+-------+--------+
| hello | 2019 |
+-------+--------+
mysql> select * from imc_class;
// * 所有列
+----------+------------+---------------------+
| class_id | class_name | add_time |
+----------+------------+---------------------+
| 1 | mysql | 2021-02-15 11:20:01 |
| 2 | mongodb | 2021-02-15 10:59:26 |
+----------+------------+---------------------+
mysql> select class_id,class_name from imc_db.imc_class;
// 只查看imc_db库下的imc_class表中class_id,class_name列数据
+----------+------------+
| class_id | class_name |
+----------+------------+
| 2 | mongodb |
| 1 | mysql |
+----------+------------+
//查询imc_course表中的title列中包含'mysql'字段的内容
select title from imc_course where title like '%mysql%';
// like:比较运算符:%为通配符
(3)比较运算符—select
(1). where==>比较运算符:>,=,<,!=,>=,<=
学习人数大于1000人的课程有哪些?列出他们的课程标题和学习人数。
- 先确定from子句:from imc_course
- 再确定select子句:select title,study_cnt
- 最后确定过滤条件where子句:where study_cnt>1000
select title,study_cnt from imc_course where study_cnt>1000;
(2). where==>比较运算符:between 上限 and 下限
学习人数大于等于1000人且小于等于2000的课程有哪些?列出他们的课程标题和学习人数。
- 先确定from子句:from imc_course
- 再确定select子句:select title,study_cnt
- 最后确定过滤条件where子句:where study_cnt between 1000 and 2000
select title,study_cnt from imc_course where study_cnt between 1000 and 2000;
//between 下限 and 上限:[上限,下限]
(3). where==>比较运算符:is null 和is not null
查询表中c1列为空的那一行的数据。
- 先确定from子句:from test_is
- 再确定select子句:select *
- 最后确定过滤条件where子句:where c1 is null
create test_is (id int, c1 varchar(10),primary key(id) );
insert into test_is values(1,'aa'),(2,null),(3,'cc');
select * from test_is where c1=null; //使用where c1=null发现结果为空,即查不到!
Empty set (0.00 sec) //所以应该使用比较运算符is null和is not null判断是否空
mysql> select * from test_is where c1 is null;
+----+------+
| id | c1 |
+----+------+
| 2 | NULL |
+----+------+
(4).比较运算符:like(% _)
比较查询字符串s1里是否包含s2
//查询字符串“this is mysql course”里是否包含“mysql”
mysql> select 'this is mysql course' like '%mysql%'; //%为通配符,表示任意多个字符
+---------------------------------------+
| 'this is mysql course' like '%mysql%' |
+---------------------------------------+
| 1 |//返回1,表明查找到了
+---------------------------------------+
mysql> select 'hao' like '_ao'; // _表示任意一个字符
+------------------+
| 'hao' like '_ao' |
+------------------+
| 1 | //返回1,查找到了
+------------------+
mysql> select 'ni hao' like '_ao';
+---------------------+
| 'ni hao' like '_ao' |
+---------------------+
| 0 |//没有查找到,返回0。因为_仅仅表示任意1个字符,所以比较不相同
+---------------------+
(3). where==>比较运算符:in 、not in
查询课程表中id为1,3,5,7,9,10的课程名称。
- 先确定from子句:from imc_course
- 再确定select子句:select title
- 最后确定过滤条件where子句:where course_id in (1,3,5,7,9,10 )
select title from imc_course where in(1,3,5,7,9,10);
查询课程表中除了id为1,3,5,7,9,10以外的课程名称。
- 先确定from子句:from imc_course
- 再确定select子句:select title
- 最后确定过滤条件where子句:where course_id not in (1,3,5,7,9,10 )
select title from imc_course where not in(1,3,5,7,9,10);
(4)逻辑运算符—select
(1). where==>逻辑运算符:and、&&
查询课程标题含有mysql关键字,且学习人数>5000人的课程标题和学习人数
- 先确定from子句:from imc_course
- 再确定select子句:select title,study_cnt
- 最后确定过滤条件where子句:where study_cnt>5000 && title like ‘%mysql%’;
select title,study_cnt from imc_course where study_cnt > 5000 && title like '%mysql%' ;
(2). where==>逻辑运算符:or、||
查询课程标题含有mysql关键字,或者学习人数>5000人的课程标题和学习人数
- 先确定from子句:from imc_course
- 再确定select子句:select title,study_cnt
- 最后确定过滤条件where子句:where study_cnt > 5000 || title like ‘%mysql%’;
select title,study_cnt from imc_course where study_cnt > 5000 || title like '%mysql%';
(3). where==>逻辑运算符:xor(异或:不同为真,相同为假)
查询–》课程标题含有mysql关键字且学习人数<5000人
- -》课程标题不含有mysql关键字且学习人数>5000人
的课程标题和学习人数
//方法1:写两个语句查询,再用union all关键字连接
select title,study_cnt from imc_course
where title like '%mysql%' && study_cnt < 5000
union all
select title,study_cnt from imc_course where title not like '%mysql%' && study_cnt > 5000;
//方法2:一个语句查询,用异或
select title,study_cnt from imc_course where study_cnt > 5000 xor title like '%mysql%'
(5)多表查询
(1) 内关联:join
查询出每一门课程的课程id、课程名称、章节名称
- 先确定from子句:来自两个表imc_course和imc_chapter,并且起别名a和b,用join关联表,on后跟两个表的关联键(连接两表的关联键):课程id
from imc_course a join imc_chapter b on a.course_id=b.course_id //关联条件 - 再确定select子句:select a.course_id,a.title,b.chapter_name
select a.course,a.title,b.chapter_name from imc_course a join imc_chapter b on a.course_id=b.course_id;
//这里内关联查询出来的是同时符合关联条件的数据。关联条件是a.course_id=b.course_id
(2) 外关联:left join和 right join
查询出每一门课程的课程id、课程名称、章节名称
我们先给imc_course插入一条新数据title假定为‘mysql关联测试’,而imc_chapter表中没有该数据,那么按照内关联查询时,查找不到该数据。故使用外关联
- 先确定from子句:来自两个表imc_course和imc_chapter,并且起别名a和b,用join关联表,on后跟两个表的关联键(连接两表的关联键):课程id
from imc_course a left join imc_chapter b on a.course_id=b.course_id //关联条件 - 再确定select子句:select a.course_id,a.title,b.chapter_name
- where子句:where title = ‘mysql 关联测试’
select a.course,a.title,b.chapter_name from imc_course a left join imc_chapter b on a.course_id=b.course_id;
//这里左外关联查询出来的是符合a表的数据及 满足a表与b表关联条件的数据。a表与b表关联条件是a.course_id=b.course_id
查询只存在于课程表中,但不存在于章节表中的课程的课程名称和课程id信息。
//法一:
select a.course_id,a.title from imc_course a where course_id not in (select b.course_id from imc_chapter b)
//法二:外关联=(异或:相同为假,不同为真)
select a.imc_course,a.title from imc_course a left join imc_chapter on a.course_id = b.course_id where b.course_id is null;
内关联:
A表 join B表 on A关联键=B关联键,即在A∩B上查找。
左关联:
A表left join B表 on A关联键=B关联键,即在A表上查找。
A表left join B表 on A关联键=B关联键,当B表关联键 is null,即在A表中且除了A∩B的部分上查找。
右关联:
A表 right join B表 on A关联键=B关联键,即在B表上查找。
A表 right join B表 on A关联键=B关联键,当A表 is null 时,即在B表中除了A∩B的部分上查找。
(6)分组统计查询
(1). group by…having
统计每个分类下不同难度的课程的数量。
查询要受到sql_mode值的影响,先用show variables like ‘sql_mode’;查找一下sql_mode的设置情况。然后设置:set session sql_mode=‘ONLY_FULL_GROUP_BY’;
- 先确定from子句:
from imc_course a join imc_class b on a.class_id = b.class_id
join imc_level c on c.level_id = a.level_id - 再确定select子句:select level_name,class_name,count(*) //聚合函数count,功能是求个数。
- 最后确定条件:group by level_name,class_name==>分组键(除了聚合函数之外的分组键)
select level_name,class_name,count(*)
form imc_course a join imc_class b on a.class_id = b.class_id
join imc_level c on c.level_id = a.level_id
group by level_name,class_name
统计每个分类下课程>3门难度的有哪些。
- 先确定from子句:
from imc_course a join imc_class b on a.class_id = b.class_id
join imc_level c on c.level_id = a.level_id - 再确定select子句:select level_name,class_name,count(*) //聚合函数count,功能是求个数。
- 最后确定过滤条件:group by level_name,class_name==>分组键(除了聚合函数之外的分组键)
不能使用聚合函数过滤条件,应该使用having进行过滤
select level_name,class_name,count(*)
form imc_course a join imc_class b on a.class_id = b.class_id
join imc_level c on c.level_id = a.level_id
//where count(*) > 3 //错误:不能使用聚合函数过滤!
group by level_name,class_name having count(*) > 3 //使用having过滤!!!
(7)聚合函数(分组函数)用法:count / sum / avg / max /min
(1) count聚合函数用法
统计课程表的总课程数
- 先确定from子句: from imc_course
- 再确定select子句:select **count(course_id),count(distinct user_id) **
//count(course_id)统计课程个数(即统计course_id这一列的行数),
//count(distinct user_id):统计讲师个数(distinct去重user_id这一列,再求行数)。
select count(course_id),count(distinct user_id) from imc_course;
(2)sum聚合函数用法
统计出所有课程的总的学习人数
- 先确定from子句: from imc_course
- 再确定select子句:select **sum(study_cnt) **
//sum(study_cnt):求总学习人数,(即求study_cnt这一列的总和)
select sum(study_cnt) from imc_course;
统计出所有课程的不同难度的课程的学习人数
- 先确定from子句:
from imc_course a join imc_level b on a.level_id = b.level_id - 再确定select子句:select level_name,sum(study_cnt)
- 最后确定过滤条件:group by level_name==>分组键(除了聚合函数之外的分组键)
select level_name,sum(study_cnt)
from imc_course a join imc_level b on a.level_name = b.level_name
group by level_name
(2)avg聚合函数用法
统计出每门课程的平均的学习人数
- 先确定from子句: from imc_course
- 再确定select子句:两种方法
法一:select sum(study_cnt)/count(study_cnt)
法二:select avg(study_cnt)
//sum(study_cnt)/count(study_cnt):求平均学习人数,(即求study_cnt这一列的总和除以study_cnt这一列的行数)
select avg(study_cnt) from imc_course;
利用课程评价表中的评分,求每门课程的平均值
- 先确定from子句: from imc_classvalue
- 再确定select子句:
select course_id,
avg(content_score) as avg_content, //计算内容评分的均值,并起别名为avg_content
avg(level_score) as avg_level, //计算分类评分的均值,并起别名为avg_level
avg(logic_score) as avg_logic, //计算逻辑评分的均值,并起别名为avg_logic
avg(score) as avg_score, //计算整体评分的均值,并起别名为avg_score - 最后确定过滤条件:group by course_id==>分组键(除了聚合函数之外的分组键)
select course_id,
avg(content_score) as avg_content,
avg(level_score) as avg_level,
avg(logic_score) as avg_logic,
avg(score) as avg_score
from imc_classvalue
group by course_id;
(2)max 、min聚合函数用法
查询出学习人数最多的课程
- 先确定from子句: from imc_course
- 再确定select子句:select title,study_cnt
- 最后确定过滤条件:
where study_cnt = (select max(study_cnt) from imc_course )
先查询学习人数最多的数量(子查询),用这个数量进行对比。
select title,study_cnt from imc_course
where study_cnt = ( select max(study_cnt) from imc_course );
(8)order by 排序用法及limit
(1)order by用法:升序asc,降序desc
查询出每门课程的学习人数,并按学习人数从高到低排序
- 先确定from子句: from imc_course
- 再确定select子句:select title,study_cnt
- 最后确定过滤条件: order by study_cnt desc
select title,study_cnt from imc_course
order by study_cnt desc;
(2)limit用法:limit 起始位置,每页要返回的记录的行数
分页返回课程id和课程名称,每页返回10行记录
- 先确定from子句: from imc_course
- 再确定select子句:select course_id,title
- 最后确定过滤条件: order by study_cnt desc limit 0,10;
select course_id,title from imc_course
order by study_cnt desc limit 0,10;
(9)创建视图
(1)定义一个包括课程id,课程名称,课程分类,课程方向以及课程难度的视图
首先先查询课程id,课程名称,课程分类,课程方向以及课程难度;
再创建视图;create view 视图名称 as select查询子句
//首先先查询课程id,课程名称,课程分类,课程方向以及课程难度
select a.course_id,a.title,b.class_name,c.type_name,d.level_name
from imc_course a
join imc_class b on a.class_id = b.class_id
join imc_type c on c.type_id = a.type_id
join imc_level d on d.level_id = a.level_id;
//再创建视图;
create view vm_course
as
select a.course_id,a.title,b.class_name,c.type_name,d.level_name
from imc_course a
join imc_class b on a.class_id = b.class_id
join imc_type c on c.type_id = a.type_id
join imc_level d on d.level_id = a.level_id;
我们用select * from vm_course就可以看到视图结果。