MySQL高级查询语句实例

常用查询介绍

在对MySQL数据库的增、删、改、查操作有一定了解之后,就可以学习一些 SQL 语句的高级使用方法。

#########数据库内容表插入###########

create database player;
use player;
create table player (id int(4) not null,name varchar(10) not null,level int(3) not null,primary key (id));
insert into player (id,name,level) values (‘30’,‘抢宝真多呀’,47);
insert into player (id,name,level) values (‘15’,‘新五皇·白胡子’,46);
insert into player (id,name,level) values (‘63’,‘新五皇–敬神’,46);
insert into player (id,name,level) values (‘199’,‘D 丶狙击王’,46);
insert into player (id,name,level) values (‘298’,‘唐三’,46);
insert into player (id,name,level) values (‘51’,‘新五皇·暴雪’,45);
insert into player (id,name,level) values (‘272’,‘D 丶抢人头辅助’,45);

select id,name,level from player where level>=45 order by level desc,id desc;
查询等级在 45 级及以上的用户,并以 level 降序排列和 id 降序排列。
select count(name),level from player where level>=45 group by level;
统计等级在 45 级及以上,以等级为分组,每个等级有多少人。
select count(name),level from player where level>=45 group by level order by count(name) desc;
查询等级在 45 级及以上, 按等级进行分组,并将每个等级的人数按降序排序

创建表 并插入信息
create table player (
-> id int(4) not null ,
-> name varchar(10) not null,
-> level int(3) not null,
-> primary key (id));
insert into player (id,name,level) values (‘1’,‘修欧拉卡’,10);
insert into player (id,name,level) values (‘2’,‘起风了’,10);
insert into player (id,name,level) values (‘3’,‘吊打低V’,15);
insert into player (id,name,level) values (‘4’,‘小花’,14);
insert into player (id,name,level) values (‘5’,‘小舞’,35);

select id,name,level from player limit 3;
select id,name,level from player order by level desc limit 3;
将查询记录按等级 level 降序排列,只取前三条记录。
select id,name,level from player limit 2,3;
即可从第 3 条记录开始显示之后的 3 条数据
select count(*) as number from player;
统计数据库表player总的行数
select p.id,p.name from player as p limit 3;
将 player 表的别名设置成 p 这个仅仅是只能在这一条命令中临时用的
select p.id,p.name from player p limit 3;
省略 as 是一样的结果

create table tmp as select * from player;
创建表tmp的时候将player表内的数据写入 tmp 表。
select count(*) from tmp;

create table player (
id int(4) not null ,
name varchar(10) not null,
level int(3) not null,
primary key (id));
insert into player (id,name,level) values (‘238’,‘sagou 轰总’,7);
insert into player (id,name,level) values (‘795’,‘senoku’,15);
insert into player (id,name,level) values (‘2460’,‘shirley’,1);
insert into player (id,name,level) values (‘448’,‘useless’,1);
insert into player (id,name,level) values (‘713’,‘guess’,25);
insert into player (id,name,level) values (‘1979’,‘Theshy’,24);
insert into player (id,name,level) values (‘2237’,‘leslieF’,3);
insert into player (id,name,level) values (‘1735’,‘oooooo’,1);
insert into player (id,name,level) values (‘2718’,‘ooo’,1);

#####################下面是通配符查询########################

select id,name,level from player where name like ‘s%’; ##name 字段以 s 开头的记录

select id,name,level from player where name like ‘%s’; ##name 字段以 s 结尾的记录

select id,name,level from player where name like ‘%es%’; ##name 字段中间含 es 的记录

select id,name,level from player where name like ‘_uess’; ##替换开头的一个字符

select id,name,level from player where name like ‘use____’; ##替换结尾的四个字符

select id,name,level from player where name like ‘shi_ley’; ###替换中间的一个字符

select id,name,level from player where name like ‘_es%’;

#########################下面是条件查询语句##################

select name,level from player where id in (select id from player where level>=45);
先查出等级大于等于45级的 ID,然后在判断player表内的ID是不是在这个结果集内,如果在就打印此行的名字和等级。

truncate table tmp; ###清空 tmp 表

insert into tmp select * from player where id in (select id from player); ####将player表的内容插入tmp 表

insert into tmp select * from player; ####可跟上面子查询 SQL 达到同样的效果

select id,name,level from tmp where id=30; ##ID 是 30 的用户等级是 47 级,最大级别

update tmp set level = level - 7 where id in (select id from tmp where level >= 47);

select id,name,level from tmp where id=30;
#可以看到等级已经少了 7 级

update tmp set level = level - 7 where id in (select a.id from (select id from tmp where level >= 47) a);
##类似于select降等级7级
select id,name,level from tmp where id=30; 可以看到ID为30 的等级下降了7

update tmp set level=47 where id=30;
将登记恢复到47
delete from tmp where id in (select a.id from (select id from tmp where level=47) a);
删除等级为47的用户
select id,name,level from tmp where id=30;
###等级为 47 的用户已经被删除

select name,level from tmp where id not in (select id from tmp where level < 45);
查询用户等级不小于 45 级的用户

select id,name,level from tmp where id = (select id from tmp where name=‘shirley’);
查询出名字是 shirley 的记录,并输出其 ID、名字和等级信息,具体操作如下所示。

select count(*) as number from tmp where EXISTS (select id from tmp where name=‘shirley’);
先通过子查询判断返回是否为TRUE,如果用户shirley存在,则计算整个tmp表的总记录数量 不存在不计算为空

NULL 值

创建一个表test
drop table test;
CREATE TABLE test (
id int(10) NOT NULL AUTO_INCREMENT,
NAME varchar(32) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL,
level int(10) NOT NULL,
coin int(32),
PRIMARY KEY (id)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

insert into test(name,level) values(‘aa’,10); ###插入的记录中不包括 coin 字段
insert into test(name,level,coin) values(‘ab’,20,100); ###插入的记录中包括 coin 字段

select * from test where coin is null; ##查询 coin 字段为空值的记录
select * from test where coin is not null; ###查询coin 字段不为空的记录

3正则表达式

匹配模式 描述 实例
^ 匹配文本的开始字符 ‘^bd’ 匹配以 bd 开头的字符串
$ 匹配文本的结束字符 ‘qn$’ 匹配以 qn 结尾的字符串
. 匹配任何单个字符 ‘s.t’ 匹配任何s 和t 之间有一个字符的字符串

  • 匹配零个或多个在它前面的字符 ‘fo*t’ 匹配 t 前面有任意个 o
  • 匹配前面的字符 1 次或多次 ‘hom+’ 匹配以 ho 开头,后面至少一个
    m 的字符串字符串 匹配包含指定的字符串 ‘clo’ 匹配含有 clo 的字符串
    p1|p2 匹配 p1 或 p2 ‘bg|fg’ 匹配 bg 或者 fg
    […] 匹配字符集合中的任意一个字符 ‘[abc]’ 匹配 a 或者 b 或者 c
    [^…] 匹配不在括号中的任何字符 ‘[^ab]’ 匹配不包含 a 或者 b 的字符串
    {n} 匹配前面的字符串 n 次 ‘g{2}’ 匹配含有 2 个 g 的字符串
    {n,m} 匹配前面的字符串至少 n 次,至多m 次 ‘f{1,3}’ 匹配 f 最少 1 次,最多 3 次

select id,name,level from player where name REGEXP ‘^us’;
在player表中查询以us开头的name字段并打印对应的id、name 和 level 记录。

select id,name,level from player where name REGEXP ‘ss$’;
在 player 表中查询以 ss 结尾的 name 字段并打印对应的 id、name 和 level 记录

select id,name,level from player where name REGEXP ‘ok’;
在player表中查询包含ok字符串的name字段并打印对应的 id、name 和 level记录

select id,name,level from player where name REGEXP ‘shir.ey’;
在player表中查询包含字符串shir 与 ey,且两个字符串之间只有一个字符的name 字段并打印对应的 id、name 和 level 记录.

select id,name,level from player where name REGEXP ‘ok|ss’;
在 player 表中查询包含字符串ok或者ss的name字段并打印对应的 id、name和 level 记录

select id,name,level from player where name REGEXP ‘oooo*’;
在 player 表中查询包含三个或者更多个连续的 o 的 name 字段并打印对应的 id、name 和 level 记录

select id,name,level from player where name REGEXP ‘oooo+’;
在player表中查询包含四个或者更多个o的 name 字段并打印对应的 id、name和 level 记录

select id,name,level from player where name REGEXP ‘1’;
在 player 表中查询包含以 d、e、f 开头的 name 字段并打印对应的 id、name 和level 记录

4、运算符

  • 加法
  • 减法
  • 乘法
    / 除法
    % 取余数
    select 1+2 as addition, 2-1 as subtraction, 2*3 as multiplication, 4/2 as division, 7%2 as remainder;
    以 SELECT 命令来实现最基础的加减乘除运算,具体操作如上所示。
    比较运算符
    运算符 描述 运算符 描述
    = 等于 IS NOT NULL 判断一个值是否不为 NULL

大于 BETWEEN AND 两者之间
< 小于 IN 在集合中
= 大于等于 LIKE 通配符匹配
<= 小于等于 GREATEST 两个或多个参数时返回最大值
!=或<> 不等于 LEAST 两个或多个参数时返回最小值
IS NULL 判断一个值是否为 NULL REGEXP 正则表达式

select 2=4,2=‘2’,‘e’=‘e’,(2+2)=(3+1),‘r’=NULL;
等于运算符在数字、字符串和表达式上的使用

SELECT ‘kgc’<>‘bdqn’, 1<>2, 3!=3, 2.5!=2, NULL<>NULL ;

大于、大于等于、小于、小于等于运算符
大于(>)运算符用来判断左侧的操作数是否大于右侧的操作数,若大于返回 1,否则返回 0,同样不能用于判断 NULL。
小于(<)运算符用来判断左侧的操作数是否小于右侧的操作数,若小于返回 1,否则返回 0,同样不能用于判断 NULL。
大于等于(>=)判断左侧的操作数是否大于等于右侧的操作数,若大于等于返回 1,否则返回 0,不能用于判断 NULL。
小于等于(<=)判断左侧的操作数是否小于等于右侧的操作数,若小于等于返回 1,否则返回 0,不能用于判断 NULL。

select 5>4,‘a’>‘b’,2>=3,(2+3)>=(1+2),4.4<3,1<2,‘x’<=‘y’,5<=5.5,‘u’>=NULL;
关于大于、大于等于、小于、小于等于运算符的使用

select 2 IS NULL,‘f’ IS NOT NULL,NULL IS NULL;
关于数字、字符和 NULL 值的运用,

select 4 BETWEEN 2 AND 6,5 BETWEEN 6 AND 8,‘c’ BETWEEN ‘a’ AND ‘f’;

SELECT least(1,2,3),least(‘a’,‘b’,‘c’),greatest(1,2,3),greatest(‘a’,‘b’,‘c’);
若要判断一组数字或字母中哪个最小、哪个最大,可以通过使用 LEAST 和GREATEST 来实现

SELECT 2 in (1,2,3,4,5),‘c’ not in (‘a’,‘b’,‘c’);
判断某数字是否在一组数字中,也可判断某字符是否在一组字符中

SELECT ‘bdqn’ LIKE ‘bdq_’,‘kgc’ LIKE ‘%c’,‘etc’ NOT LIKE ‘%th’;
若要判断某字符串能否匹配成功,分单字符匹配和多字符匹配,也可以判断不匹配

、逻辑运算符

NOT 或 ! 逻辑非
AND 或 && 逻辑与
OR 或 || 逻辑或
XOR 逻辑异或

SELECT not 2,!3,not 0,!(4-4);
对非 0 值和 0 值分别作逻辑非运算

SELECT 2 AND 3,4 && 0,0 && NULL,1 AND NULL;
对非 0 值、0 值和 NULL 值分别作逻辑与运算

SELECT 2 OR 3,4 or 0,0 OR NULL,1 || NULL;
对非 0 值、0 值和 NULL 值分别作逻辑或运算

SELECT 2 XOR 3,0 XOR 0,0 XOR 5,1 XOR NULL,NULL XOR NULL;
对非0 值、0 值和 NULL 值分别作逻辑异或运算

位运算符

& 按位与
| 按位或
~ 按位取反
^ 按位异或
<< 按位左移

按位右移

SELECT 10 & 15, 10 | 15, 10 ^ 15, 5 &~1;
对数字进行按位与、或和取反运算10 转换为二进制数是 1010, 15 转换为二进制数是 1111

SELECT 1<<2, 2<<2,10>>2,15>>2;
对数字进行左移或右移的运算

运算符的优先级
优先级 运算符 优先级 运算符
1 ! 8 |
2 ~ 9 =,<=>,>=,>,<=,<,<>,!=,IS,LIKE,REGEXP,IN
3 ^ 10 BETWEEN,CASE,WHEN,THEN,ELSE
4 * , /(DIV), %(MOD) 11 NOT
5 +,- 12 &&,AND
6 >>,<< 13 ||,OR,XOR
7 & 14 :=

连接查询

1、为了便于理解,这里使用两个表 a_player 和 b_player 来进行演示。首先需要创建这两个表,然后插入一些初始数据。

CREATE TABLE a_player (
a_id int(11) DEFAULT NULL,
a_name varchar(32) DEFAULT NULL,
a_level int(11) DEFAULT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

CREATE TABLE b_player (
b_id int(11) DEFAULT NULL,
b_name varchar(32) DEFAULT NULL,
b_level int(11) DEFAULT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

insert into a_player(a_id, a_name, a_level) values(1, ‘aaaa’, 10);
insert into a_player(a_id, a_name, a_level) values(2, ‘bbbb’, 20);
insert into a_player(a_id, a_name, a_level) values(3, ‘cccc’, 30);
insert into a_player(a_id, a_name, a_level) values(4, ‘dddd’, 40);

insert into b_player(b_id, b_name, b_level) values(2, ‘bbbb’, 20);
insert into b_player(b_id, b_name, b_level) values(3, ‘cccc’, 30);
insert into b_player(b_id, b_name, b_level) values(5, ‘eeee’, 50);
insert into b_player(b_id, b_name, b_level) values(6, ‘ffff’, 60);

1.内连接 内连接的语法格式如下。
SELECT column_name(s)FROM table1 INNER JOIN table2 ON table1.column_name = table2.column_name;

select a_id,a_name,a_level from a_player inner join b_player on a_id=b_id;
在刚才创建的 a_player 和 b_player 表中使用内连接查询出通过判断 a_id 和 b_id 相等,包含在两个表内的部分

select * from a_player a left join b_player b on a.a_id=b.b_id;
查询出 a_player 表中所有内容,并且查询出通过 a_id 和 b_id 相等判断出的 b_player 中的部分

select * from a_player a right join b_player b on a.a_id=b.b_id;
从 a_player 和 b_player 表中,查询出在 b_player 表内的所有记录,并且通过判断 a_id 和 b_id 相等,在 a_player 表内的部分

2、数据库函数

数学函数 描述
abs(x) 返回 x 的绝对值
rand() 返回 0 到 1 的随机数
mod(x,y) 返回 x 除以 y 以后的余数
power(x,y) 返回 x 的 y 次方
round(x) 返回离 x 最近的整数
round(x,y) 保留x 的y 位小数四舍五入后的值
sqrt(x) 返回 x 的平方根
truncate(x,y) 返回数字 x 截断为 y 位小数的值
ceil(x) 返回大于或等于 x 的最小整数
floor(x) 返回小于或等于 x 的最大整数
greatest(x1,x2…) 返回集合中最大的值
least(x1,x2…) 返回集合中最小的值
select abs(-1), rand(), mod(5,3), power(2,3), round(1.89);
MySQL 数学函数的使用方法
select round(1.8937,3), truncate(1.235,2), ceil(5.2), floor(2.1), least(1.89,3,6.1,2.1);

2.聚合函数
聚合函数 描述
avg() 返回指定列的平均值
count() 返回指定列中非 NULL 值的个数
min() 返回指定列的最小值
max() 返回指定列的最大值
sum(x) 返回指定列的所有值之和
例如,MySQL 聚合函数的使用方法,具体操作如下所示。

select sum(level) as sum_level from player;
select max(level) as max_level from player;
select min(level) as min_level from player;

3.字符串函数
字符串函数 描述
length(x) 返回字符串 x 的长度
trim() 返回去除指定格式的值
concat(x,y) 将提供的参数 x 和 y 拼接成一个字符串
upper(x) 将字符串 x 的所有字母变成大写字母
lower(x) 将字符串 x 的所有字母变成小写字母
left(x,y) 返回字符串 x 的前 y 个字符
right(x,y) 返回字符串 x 的后 y 个字符
repeat(x,y) 将字符串 x 重复 y 次
space(x) 返回 x 个空格
replace(x,y,z) 将字符串 z 替代字符串 x 中的字符串 y
strcmp(x,y) 比较 x 和 y,返回的值可以为-1,0,1
substring(x,y,z) 获取从字符串 x 中的第 y 个位置开始长度为 z 的字符串
reverse(x) 将字符串 x 反转
MySQL 字符串函数的使用方法,具体操作如下所示。
mysql>select length(‘bdqn’), trim(’ yellow '), concat(‘bd’, ‘qn’), upper(‘abc’), right(‘hello’, 3);

select repeat(‘kgc’, 2), replace(‘hello’, ‘ll’, ‘kgc’), strcmp(4, 5), substring(‘bjbdqn’, 4, 2), reverse(‘hello’);

4.日期时间函数
字符串函数 描述
curdate() 返回当前时间的年月日
curtime() 返回当前时间的时分秒
now() 返回当前时间的日期和时间
month(x) 返回日期 x 中的月份值
week(x) 返回日期 x 是年度第几个星期
hour(x) 返回 x 中的小时值
minute(x) 返回 x 中的分钟值
second(x) 返回 x 中的秒钟值
dayofweek(x) 返回 x 是星期几,1 星期日,2 星期一
dayofmonth(x) 计算日期 x 是本月的第几天
dayofyear(x) 计算日期 x 是本年的第几天

MySQL 日期时间函数的使用方法
select curdate(),curtime(),now(),month(‘2020-02-09’),week(‘2020-02-09’), hour(‘21:13:53’);

select minute(‘21:13:53’),second(‘21:13:53’),dayofweek(‘2020-02-09’), dayofmonth(‘2020-02-09’), dayofyear(‘2020-02-09’);

创建存储函数调用#

mysql> DELIMITER m y s q l > C R E A T E P R O C E D U R E P l a y e r R o l e ( ) B E G I N S E L E C T i d , n a m e , l e v e l f r o m p l a y e r l i m i t 3 ; E N D mysql>CREATE PROCEDURE PlayerRole() BEGIN SELECT id,name,level from player limit 3; END mysql>CREATEPROCEDUREPlayerRole()BEGINSELECTid,name,levelfromplayerlimit3;END
mysql> DELIMITER ; #注意这里分号前有空格。
mysql> call PlayerRole;

通过存储过程查询 player 表中某一条记录,存储过程是带参数的,具体操作如下所示。
mysql>DELIMITER C R E A T E P R O C E D U R E G e t R o l e ( I N i n n a m e V A R C H A R ( 16 ) ) B E G I N S E L E C T i d , n a m e , l e v e l f r o m p l a y e r w h e r e n a m e = i n n a m e ; E N D CREATE PROCEDURE GetRole(IN inname VARCHAR(16)) BEGIN SELECT id,name,level from player where name=inname; END CREATEPROCEDUREGetRole(INinnameVARCHAR(16))BEGINSELECTid,name,levelfromplayerwherename=inname;END
mysql>DELIMITER ;
mysql>call GetRole(‘shirley’);

修改存储
DROP PROCEDURE PlayerRole;

CALL PlayerRole;


  1. d-f ↩︎

猜你喜欢

转载自blog.csdn.net/Laiyunpeng666/article/details/108716826