SQL语句(四)联表查询
一、关联查询的分类
按年代分
sql92
:仅仅支持内连接
sql99
【推荐】:支持内连接
+外连接(左外,右外)
+交叉连接
按功能分
- 内连接
- 等值连接
- 非等值连接
- 自连接
- 外连接
- 左外连接
- 右外连接
- 全外连接
- 交叉连接
二、sql92语法的连接
语法
SELECT 查询列表
FROM 待链接的多个表
WHERE 连接条件 [和筛选条件]
这里的连接条件写字段相等关系,如e.department_id = d.id
等
1. 简单应用
查询员工名
和对应的部门名
SELECT last_name 员工名,department_name 部门名
FROM employees, departments
WHERE employees.department_id=departments.department_id;
# 连接条件为employees.department_id=departments.department_id
2. 为表起别名
SELECT 查询列表
FROM 表名 AS 别名, ...
WHERE 连接条件等
查询员工名
,工种号
,工种名
SELECT last_name,e.job_id,job_title
FROM employees AS e, jobs AS j
WHERE e.job_id = j.job_id;
由于两个表中都有job_id这个字段,所以在SELECT
中需要指明是哪张表
3. 加入筛选
查询有奖金的
员工名
,部门名
SELECT e.last_name, d.department_name
FROM employees e, departments d
WHERE e.department_id = d.department_id
AND e.commission_pct IS NOT NULL; <--加入的筛选条件
查询位于的城市的城市名中第二个字符为o
的部门名
和城市名
SELECT city,department_name
FROM locations l,departments d
WHERE d.location_id=l.location_id
AND city LIKE '_o%';
4. 加入分组
查询每个城市
的部门个数
SELECT city,COUNT(*) 部门个数
FROM locations l,departments d
WHERE l.location_id=d.location_id
GROUP BY city
查询每个工种
的工种名
和员工个数
,并按员工个数降序
SELECT job_title,COUNT(*) 员工个数
FROM jobs j,employees e
WHERE j.job_id=e.job_id
GROUP BY job_title
ORDER BY 员工个数 DESC;
5. 三表连接
和两表连接是基本相同的,在WHERE
语句中加入一个连接条件即可
获取所有员工的员工名
,部门名
和所在城市
SELECT last_name, department_name, city
FROM employees e, departments d, locations l
WHERE e.department_id = d.department_id
AND d.location_id = l.location_id;
6. 非等值连接
查询员工的工资
和工资级别
job_grades
表:
SELECT salary, grade_level
FROM employees e, job_grades j
WHERE e.salary >= j.lowest_sal AND e.salary <= j.highest_sal;
7. 自连接
查询员工名及其对应上级的名称
SELECT e.last_name 员工,m.last_name 上级
FROM employees e, employees m
WHERE e.manager_id=m.employee_id;
三、sql99语法的连接
SELECT 查询列表
FROM 表1别名
【连接类型】 join 表2 别名
on 连接条件
where xxx
连接类型分类
- 内连接:
inner
和sql92
的等值连接是等效的 - 外连接:
- 左外:
left [outer]
- 右外:
right [outer]
- 全外:
full [outer]
- 左外:
- 交叉连接:
cross
1. 内连接(INNER JOIN)
获取所有的员工名
和其对应的部门名
SELECT e.last_name, d.department_name
FROM employees e INNER JOIN departments d
ON e.department_id = d.department_id;
查询部门个数>3
的城市名
和部门个数
SELECT city, COUNT(1) 部门个数
FROM departments d INNER JOIN locations l
ON d.location_id = l.location_id
GROUP BY city
HAVING 部门个数 > 3;
查询员工名、部门名、工种名,并按部门名排序【三表连接】
SELECT last_name, department_name, job_title
FROM employees e INNER JOIN departments d
ON e.department_id = d.department_id
INNER JOIN jobs j
ON e.job_id = j.job_id
ORDER BY department_name DESC;
查询员工的工资级别【非等值连接】
SELECT last_name, salary, grade_level
FROM employees e INNER JOIN job_grades j
ON e.salary BETWEEN j.lowest_sal AND j.highest_sal
ORDER BY salary;
查询员工名即其对应的上级名【自连接】
SELECT e.last_name 员工名, m.last_name 上级名
FROM employees e INNER JOIN employees m
ON e.manager_id = m.employee_id;
由上面的例子可以看出,使用sql99的内连接(INNER JOIN)
即可实现sql92的所有连接操作了。
2. 外连接
作用:查询一个表有
,另一个表没有
的记录
先使用girls.sql
生成对应的数据,对应的文件可以在https://www.bilibili.com/video/BV12b411K7Zu?from=search&seid=2415880702283399133 这个b站视频的评论区中找到。
此时我们可以获得如下几张表:
然后我们可以分别使用内连接和外连接分别连接beauty
和boys
这两张表,查看结果的差异:
内连接:
SELECT *
FROM beauty b INNER JOIN boys y
ON b.boyfriend_id = y.id;
外连接(左外):
SELECT *
FROM beauty b LEFT JOIN boys y
ON b.boyfriend_id = y.id;
可以发现,当左表
(即beauty
表)的boyfriend_id
字段找不到boys
表中对应的id
进行连接时,它也仍会保留这一记录,而右表(即boys
表)的记录则全部设置为Null
。
一句话来说,就是左表的数据不管是否满足连接条件,都至少会保留在最终查询集的一条记录之中。
查找男朋友不在男神表的女神名【左外连接】:
SELECT `name`, boyName
FROM beauty b LEFT JOIN boys y
ON b.boyfriend_id = y.id
WHERE y.id IS NULL;
【右外连接】
SELECT `name`, boyName
FROM boys y RIGHT JOIN beauty b
ON b.boyfriend_id=y.id
WHERE y.id IS NULL;
查询没有联系女神
的男生
SELECT `name`, boyName
FROM beauty b RIGHT JOIN boys y
ON b.boyfriend_id=y.id
WHERE b.id IS NULL;
查询哪个部门
没有员工
SELECT department_name, COUNT(*)
FROM departments d LEFT JOIN employees e
ON d.department_id = e.department_id
GROUP BY department_name
HAVING COUNT(*)=0;
3. 交叉连接
SELECT b.`name`, y.boyName
FROM beauty b CROSS JOIN boys y;
即返回笛卡尔积
(即所有组合的可能),左表数据为m
条,右表数据为n
条,最终查询集数据为m * n
条
SQL语句(四)联表查询的更多相关文章
- 使用linq语句进行联表查询
假设你有一个父表(例如:汽车),其关联一个子表,例如轮子(一对多).现在你想对于所有的父表汽车,遍历所有汽车,然后打印出来所有轮子的信息.默认的做法将是: SELECT CarId FROM Cars ...
- SQL 一对多联表查询最大值
有两个数据表City表和Price表,CIty表的结构如下: Price表的结构如下: 查询每个城市最大的销售价格,并以最大价格进行降序排列,选取前5条记录,SQL语句的代码如下: * from (s ...
- 2.1 Oracle之DML的SQL语句之单表查询以及函数
1.SQL简介 对于不同的数据库来说,SQL语句是相通的,关系型数据库都以SQL语句为操作的标准,只是相应的数据库对应的函数不相同. SQL(Structured Query Language,结构化 ...
- 2.2 Oracle之DML的SQL语句之多表查询以及组函数
一.SQL的多表查询: 1.左连接和右连接(不重要一方加(+)) SELECT e.empno,e.ename,d.deptno,d.dname,d.loc FROM emp e,dept d WHE ...
- SQL语句 自连表查询。inner join用法,partition by ,列转行查询
use mydb1 go -- 表T_Employee2 -- Id Name Position Dept -- 1 张三 员工 市场部 -- 2 李四 经理 销售部 -- 3 王五 经理 市场部 - ...
- 惊世骇俗的sql语句之连表查询
select `product_skus`.id as skuId, `wname` as sku名称, if(`sku_attributes`.`status`=1,'上架','下架') as 状态 ...
- sql学习笔记(三)—— 联表查询
上篇写了一些sql查询的知识,这篇接着写一下有关联表查询的知识. 既然是联表查询,那肯定得多个表啊,所以,我们先创建一个教师表,表名为 teacher,并且向表中插入数据. 准备工作: 创建表语句: ...
- ThinkPHP---TP功能类之联表查询
[一]介绍 在原生的sql中使用join 语法进行数据的联表查询, 在ThinkPHP里支持联表查询操作,但是可以归纳成两种方式:table方法.join方法 (1)table方法:在TP中对应SQL ...
- SQL联表查询
数据库中最最常用的语法----select.简单的select语法很直白: select column from table where expression: 从((from)存储数据的地方(tab ...
- Mybatis入门(四)------联表查询
Mybatis联表查询 一.1对1查询 1.数据库建表 假设一个老师带一个学生 CREATE TABLE teacher( t_id INT PRIMARY KEY, t_name VARCHAR(3 ...
随机推荐
- 关于equals()和hashcode()的一些约定
本文章主要讨论和回答一下几个问题: equals()的四大特性 equals()和hashcode()之间的关系,为什么我们经常说这两个方法要么都重写,要么都不重写? HashMap.HashSet等 ...
- 配置中心之Nacos简介,使用及Go简单集成
简介 为什么需要配置中心 我们现在有一个项目, 使用Gin进行开发的, 配置文件我们知道是一个config.yaml的文件, 也知道这个配置文件在项目启动时会被加载到内存中使用; 考虑三种情况: ...
- 『心善渊』Selenium3.0基础 — 16、Selenium对iframe表单的操作
目录 1.什么是iframe表单 2.iframe表单操作流程 3.iframe表单操作常用方法 (1)进入表单 (2)多表单切换 4.表单操作示例 1.什么是iframe表单 实际上就是HTML页面 ...
- Pandas高级教程之:plot画图详解
目录 简介 基础画图 其他图像 bar stacked bar barh Histograms box Area Scatter Hexagonal bin Pie 在画图中处理NaN数据 其他作图工 ...
- C++ nullptr 和 NULL 的使用区别
1. 为什么会有nullptr的出现 目的:nullptr的出现主要是为了替代NULL. 那么,为什么要替代NULL呢? 在NULL的定义中存在会有2种方式,有的编译器会将NULL定义成0,有的编译器 ...
- Mysql 主键的操作
主键:primary key ,主要的键.一张表只能有一个字段可以使用对应的键,用来唯一的约束字段里面的数据,数据不能重复,这种键称之为主键,一张表只能最多有一个主键. 一.增加主键 方法一:在 ...
- Entity Framework Core中的数据迁移命令
使用程序包管理控制台输入命令. 数据迁移命令: Add-Migration 对比当前数据库和模型的差异,生成相应的代码,使数据库和模型匹配的. Remove-Migration 删除上次的迁移 Sc ...
- Java | this的本质 和 static的本质
this 在说this之前先说一下,对象创建的过程: 1.分配对象空间,并将对象成员变量初始化. 2.执行属性值的显式初始化. 3.执行构造方法. 4.返回相关的地址给相关的对象. this的本质 ...
- WIN10家庭版 访问WINXP 共享打印机
WIN10家庭版 1.安装对应的打印机驱动 2.打开WIN10计算机---在地址栏中输入:\\计算机XP名称,显示对应的共享资源,直接选择即可.如果无法访问则进行如下第三步 3.设置过程 开始 -设置 ...
- 【Azure Redis 缓存】云服务Worker Role中调用StackExchange.Redis,遇见莫名异常(RedisConnectionException: UnableToConnect on xxx 或 No connection is available to service this operation: xxx)
问题描述 在Visual Studio 2019中,通过Cloud Service模板创建了一个Worker Role的角色,在角色中使用StackExchange.Redis来连接Redis.遇见了 ...