mysql多表查询、子查询、函数详解

多表查询

在这里插入图片描述

交叉查询

##########交叉查询(没用)或者笛卡尔积查询:多个表的数据的乘积
#问题:大量数据的冗余 , 在多表查询中 多表查询建立在笛卡尔积的基础上
##语法:select * from A , B, C,D.....
SELECT * FROM dept , emp;
SELECT COUNT(*) FROM dept , emp;

内连接

###########显示内连接
#语法: select * from A inner join B  on 连接的条件	
#		       inner join C  on 连接的条件
#		       inner join D  on 连接的条件  ...
SELECT * FROM dept INNER JOIN emp ON emp.dept_id=dept.id;
#细节 : 隐式内连接 对sql足够熟悉使用  显示内连接初学者使用
#细节 : 无论是哪一种内连接 最后的查询结果不会发生变化 , 只是字段顺序变化了
#细节 : 如果整个表中有且唯一的字段可以省略表名(建议不要省略)
#细节 : 如果单词过长 可以加入表别名 通过别名.字段 快速获得字段

左外连接和右外连接

##########外连接 : 结果跟表的放置顺序有关系
###########左外连接
#语法: select * from A 	left join B on 连接条件
#			left join C on 连接条件
#			left join D on 连接条件...
#以左表为主 将左表的数据全部查询出来 ,匹配右表的数据, 匹配成功正常显示数据
#匹配失败 , 右表数据以null方式展示 
SELECT * FROM dept AS d 
	LEFT JOIN emp AS e ON d.id =  e.dept_id;
SELECT * FROM  emp AS e
	LEFT JOIN dept AS d ON d.id =  e.dept_id;
###########右外连接
#以右表为主 将右表的数据全部查询出来 ,匹配左表的数据, 匹配成功正常显示数据
#匹配失败 , 左表数据以null方式展示 
#语法: select * from A 	right join B on 连接条件
#			right join C on 连接条件
#			right join D on 连接条件...
SELECT * FROM dept AS d 
	RIGHT JOIN emp AS e ON d.id =  e.dept_id;
	
SELECT * FROM  emp AS e
	LEFT JOIN dept AS d ON d.id =  e.dept_id;

/*
select * from A,B,C,D..... where 连接的条件 and  where 连接的条件 基于笛卡尔积
非标准语法:  不建议inner省略  建议 outer省略
#语法: select * from A [inner] join B  on 连接的条件	
#		       [inner] join C  on 连接的条件
#		       [inner] join D  on 连接的条件  ...
#语法: select * from A 	left [outer] join B on 连接条件
#			left [outer] join C on 连接条件
#			left [outer] join D on 连接条件
#语法: select * from A 	right [outer] join B on 连接条件
#			right [outer] join C on 连接条件
#			right [outer] join D on 连接条件...

*/

子查询

即一条SELECT语句结果作为另一条SELECT语法一部分(作为查询条件或查询结果或表)

#一条SELECT语句结果作为另一条SELECT语法一部分(作为查询条件或查询结果或表)
#其实就是逻辑语句嵌套
#案例:查询emp表中工资最高的员工信息
#select * from emp where salary = 9000;
SELECT * FROM emp WHERE MAX(salary) = 9000;

#查询最高工资(一条SELECT语句结果)
SELECT MAX(salary) FROM emp;
#根据工资查询员工
SELECT * FROM emp  WHERE salary = 最高工资(变量) ;

#演变 :子查询 ()  ()中加入另外一条sql即可   (作为另一条SELECT语法一部分)
SELECT * FROM emp  WHERE salary = ( SELECT MAX(salary) FROM emp ) ;

#查询工资小于平均工资的员工有哪些
#平均工资
SELECT AVG(salary) FROM emp;
#查询工资小于平均工资的员工
SELECT * FROM emp WHERE salary < 平均工资
#演变
SELECT * FROM emp WHERE salary < ( SELECT AVG(salary) FROM emp );

#3.查询工资大于5000的员工,来自于哪些部门的名字
#3.1先查询大于5000的员工所在的部门id
SELECT dept_id FROM emp WHERE salary > 5000; #(1,2 ,null)

#3.2再查询在这些部门id中部门的名字
#Subquery returns more than 1 row 如果是等号 
# 如果最后返回的结果是单行单列 使用等号表示
# 如果最后返回的结果是单列多行 使用in表示
SELECT * FROM dept WHERE id IN (SELECT dept_id FROM emp WHERE salary > 5000)

SELECT * FROM emp;
SELECT * FROM dept;

#案例:查询市场部下的员工信息有哪些
#查询出市场部的id值 
SELECT id FROM dept WHERE NAME='市场部';
#根据部门的id 找员工表中对于的信息即可
SELECT * FROM emp WHERE dept_id = (SELECT id FROM dept WHERE NAME='市场部');

#案例:查询开发部与财务部所有的员工信息
#查询开发部与财务部 的id值
SELECT id FROM dept WHERE NAME IN ('开发部','财务部');

#查询员工信息
SELECT * FROM emp WHERE dept_id IN ( SELECT id FROM dept WHERE NAME IN ('开发部','财务部') ) ;

#子查询能作为表存在 那么内连接和外连接一定也能够完成
#子查询:作为表存在
#查询出2011年以后入职的员工信息,包括部门名称
#员工信息 部门名称 -> 要多表查询 -> 查询出2011年以后入职
SELECT * FROM dept d , emp e 
	WHERE d.id = e.dept_id  
	AND join_date > '2011-01-01' ;

#SELECT * FROM1 , (通过子查询的方式查询表)
#	WHERE1.字段 =2.字段
#	AND 条件 ;
#子查询
SELECT *
	FROM dept d , (SELECT NAME,salary,join_date,dept_id FROM emp) e 
	WHERE d.id = e.dept_id  
	AND join_date > '2011-01-01' ;

SELECT * FROM emp;

备份和还原

灾备 : 灾难备份(服务器宕机 磁盘损坏) 一般来说由程序每天自动备份
bin : 可执行文件 或者 批处理目录
命令行的方式
备份格式: mysqldump -u用户名 -p密码 数据库 > 文件的路径
还原格式: SOURCE 导入文件的路径;
注意:还原的时候需要先登录MySQL,并选中对应的数据库
备份的时候 不需要登录到数据库中
​ > 在系统中 表示 写入到某个文件
​ mysqldump -uroot -proot 需要备份的数据库名称 > 文件的路径
​ mysqldump -uroot -proot day03_02 > d:/data.sql
通过命令行到处的数据库 没有创建库的 create database
还原的时候 必须登录到数据里,要选择库
使用source 文件的路径
先创建库 create database 库
使用库 use 库名称
source d:/data.sql
工具的方式
备份
在这里插入图片描述
还原
在这里插入图片描述

函数

字符串函数

1.  函数:CONCAT(s1,s2...sn)
	描述:字符串 s1,s2 等多个字符串合并为一个字符串
	实例:SELECT CONCAT("阿", "里", "巴", "巴");
	
2.  函数:CHAR_LENGTH(str)
	描述:返回字符串 str 的字符数(长度)
	实例:SELECT CHAR_LENGTH("阿里巴巴");
	
3.  函数:LENGTH(str)
	描述:返回字符串 s 的字节数(长度)
	实例:SELECT LENGTH("阿里巴巴") ;
	
4.  函数:UCASE(s) | UPPER(s)
	描述:将字符串转换为大写
	实例:SELECT UCASE("Alibaba");
	
5.  函数:LCASE(s) | LOWER(s)
	描述:将字符串转换为小写
	实例:SELECT LCASE("ALIBABA");
	
6.  函数:LOCATE(s1,s)
	描述:从字符串 s 中获取 s1 的开始位置
	实例:SELECT LOCATE('ao','hhaoheia');
	
7.  函数:TRIM(str) | LTRIM(str) | RTRIM(str)
	描述:字符串去空格
	实例:SELECT TRIM("  taikonr");
	
8.  函数:REPLACE(s,s1,s2)
	描述:将字符串 s2 替代字符串 s 中的字符串 s1
	实例:SELECT REPLACE('abc','a','x');
	
9.  函数:SUBSTR(s, start, length)
	描述:从字符串 s 的 start 位置截取长度为 length 的子字符串
	实例:SELECT SUBSTR("hhhsll", 2, 3);
	
10. 函数:STRCMP(str1,str2)
	描述:比较字符串大小,左大于右时返回1,左等于右时返回0,,左小于于右时返回-1,
	实例:SELECT STRCMP("a","b");

日期函数

1.  函数:NOW() | CURDATE() | CURTIME()
	描述:获取系统当前日期时间、日期、时间
	实例:SELECT NOW();
	
2.  函数:YEAR(DATE) | MONTH(DATE) | DAY(DATE)
	描述:从日期中选择出年、月、日
	实例:SELECT YEAR(NOW()); 
	
3.  函数:LAST_DAY(DATE)
	描述:返回月份的最后一天
	实例:SELECT LAST_DAY(NOW());
	
4.  函数:ADDDATE(DATE,n) | SUBDATE(DATE,n)
	描述:计算起始日期 DATE 加(减) n 天的日期
	实例:SELECT ADDDATE(NOW(),10);
	
5.  函数:QUARTER(DATE)
	描述:返回日期 DATE 是第几季节,返回 14
	实例:SELECT QUARTER(NOW());
	
6.  函数:DATEDIFF(d1,d2)
	描述:计算日期 d1->d2 之间相隔的天数
	实例:SELECT DATEDIFF('2019-08-01','2019-07-01');
	
7.  函数:DATE_FORMAT(d,f)
	描述:按表达式 f的要求显示日期 d
	实例:SELECT DATE_FORMAT(NOW(),'%Y-%m-%d');

-- 统计每个员工入职的天数
SELECT DATEDIFF(NOW(),joindate) FROM emp;
-- 统计每个员工的工龄
SELECT DATEDIFF(NOW(),joindate)/365 FROM emp;
-- 查询2011年入职的员工
SELECT * FROM emp WHERE YEAR(joindate) = 2011;
-- 统计入职10年以上的员工信息
SELECT * FROM emp WHERE (DATEDIFF(NOW(),joindate)/365) > 10;

数字函数

1.  函数:ABS(x)
	描述:返回 x 的绝对值  
	实例:SELECT ABS(-1);
	
2.  函数:CEIL(x) | FLOOR(x)
	描述:向上(下)取整
	实例:SELECT CEIL(1.5);
	
3.  函数:MOD(x,y)
	描述:返回x mod y的结果,取余
	实例:SELECT MOD(5,4);
	
4.  函数:RAND()
	描述:返回 01 的随机数
	实例:SELECT RAND();
	
5.  函数:ROUND(x)
	描述:四舍五入
	实例:SELECT ROUND(1.23456);
	
6.  函数:TRUNCATE(x,y)
	描述:返回数值 x 保留到小数点后 y 位的值
	实例:SELECT TRUNCATE(1.23456,3);

-- 统计每个员工的工龄,超过半年的算一年
SELECT ROUND(DATEDIFF(NOW(),joindate)/365) FROM emp;
-- 统计每个部门的平均薪资,保留2位小数
SELECT dept_id,TRUNCATE(AVG(salary),2) FROM emp GROUP BY dept_id;
-- 统计每个部门的平均薪资,小数向上取整
CEIL()
-- 统计每个部门的平均薪资,小数向下取整
FLOOR()	
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值