一、准备工作

-- create
CREATE TABLE EMPLOYEE (
empId int,
name varchar(15),
dept varchar(10)
);
-- insert
INSERT INTO EMPLOYEE(empId,name,dept) VALUES (1, 'Clark', 'Sales'), (2, 'Dave', 'Accounting'),(3, 'Ava', 'Sales');
-- query
SELECT * FROM EMPLOYEE WHERE dept = 'Sales';
根据上面的sql,将下面三个表转化成创建表、插入数据、查询数据的sql
employees 表:
employee_id | name | department_id
------------|---------|---------------
1 | Alice | 101
2 | Bob | 102
3 | Charlie | 103
departments 表:
department_id | department_name
--------------|-----------------
101 | HR
102 | IT
103 | Finance
salaries 表:
employee_id | salary
------------|--------
1 | 50000
2 | 60000
3 | 70000
二、sql在线练习网站
dbfiddle:这个网站更好
onecompiler:这个网站一般
-- ======================
-- create表
-- ======================
CREATE TABLE employees (
employee_id int,
name varchar(15),
department_id int
);
CREATE TABLE departments (
department_id int,
department_name varchar(15)
);
CREATE TABLE salaries (
employee_id int,
salary int
);
-- ======================
-- insert数据
-- ======================
INSERT INTO employees(employee_id, name, department_id)
VALUES (1, 'Alice', 101),
(2, 'Bob', 102),
(3, 'Charlie', 103);
INSERT INTO departments(department_id, department_name)
VALUES (101, 'HR'),
(102, 'IT'),
(103, 'Finance');
INSERT INTO salaries(employee_id, salary)
VALUES (1, 50000),
(2, 60000),
(3, 70000);
-- ======================
-- query查询
-- ======================
-- 1、员工表
SELECT * FROM employees;
-- 2、部门表
SELECT * FROM departments;
-- 3、薪资表
SELECT * FROM salaries;
-- 4、查询所有员工 + 部门名称
SELECT
e.employee_id,
e.name,
d.department_name
FROM employees e
INNER JOIN departments d
ON e.department_id = d.department_id;
-- 5、查询所有员工 + 部门 + 薪资
SELECT
e.employee_id,
e.name,
d.department_name,
s.salary
FROM employees e
INNER JOIN departments d
ON e.department_id = d.department_id
INNER JOIN salaries s
ON e.employee_id = s.employee_id;
-- 6、子查询:查询所有员工 + 部门 + 薪资,【子查询先把 salaries 表筛选出来当作临时表,再与其它表 INNER JOIN(子查询在 FROM 中,派生表)】
SELECT e.employee_id,
e.name,
d.department_name,
s.salary
FROM employees e
INNER JOIN departments d
ON e.department_id = d.department_id
INNER JOIN (
SELECT employee_id, salary
FROM salaries
) s
ON e.employee_id = s.employee_id;
-- 7、子查询:查询薪资高于平均薪资的员工 + 部门名称 + 薪资
SELECT
e.employee_id,
e.name,
d.department_name,
s.salary
FROM employees e
INNER JOIN departments d
ON e.department_id = d.department_id
INNER JOIN salaries s
ON e.employee_id = s.employee_id
WHERE s.salary > (
SELECT AVG(salary)
FROM salaries
);
-- 8、子查询:查询在IT部门工作的员工,【先执行子查询找出 IT 部门的 department_id,再用结果过滤员工(子查询在 WHERE 中)】
SELECT
employee_id,
name
FROM employees
WHERE department_id IN (
SELECT department_id
FROM departments
WHERE department_name = 'IT'
);
-- 9、子查询:查询所有员工的工资【每个员工记录都用子查询找对应的薪资(子查询在 SELECT 中,标量子查询)】
SELECT
employee_id,
name,
(SELECT salary FROM salaries WHERE salaries.employee_id = employees.employee_id) AS salary
FROM employees;
-- 10、把employees表里employee_id为3的department_id更新为104
UPDATE employees
SET department_id = 104
WHERE employee_id = 3;
-- 11、再次查看员工表
SELECT * FROM employees;
-- 12、删除employees表里employee_id为3的数据
DELETE FROM employees
WHERE employee_id = 3;
-- 13、再次查看员工表
SELECT * FROM employees;
三、补充
-- 单表查询
SELECT * FROM Def_Department WHERE IsValid = 1
-- 单表查询通过部门分组
SELECT Department,COUNT(*) AS UserCount FROM Def_Department WHERE IsValid = 1 GROUP BY Department
-- 单表查询通过部门分组后筛选条件(行数大于82)
SELECT Department,COUNT(*) AS UserCount FROM Def_Department WHERE IsValid = 1 GROUP BY Department HAVING COUNT(*) > 82
-- 单表查询通过部门分组后筛选条件(行数大于82)再通过条件进行排序(通过行数排序,默认asc升序),备注:HAVING不能引用别名,只能用字段名或者COUNT(*)等聚合函数,ORDER BY既可以用别名,也可以用字段名或者COUNT(*)等聚合函数
SELECT Department,COUNT(*) AS UserCount FROM Def_Department WHERE IsValid = 1 GROUP BY Department HAVING COUNT(*) > 82 ORDER BY UserCount DESC
-- 限制,取前10条记录
SELECT Department,COUNT(*) AS UserCount FROM Def_Department WHERE IsValid = 1 GROUP BY Department HAVING COUNT(*) > 82 ORDER BY UserCount DESC LIMIT 10
-- 分页,跳过第0条,从第1条开始取,取100条记录
SELECT Department,COUNT(*) AS UserCount FROM Def_Department WHERE IsValid = 1 GROUP BY Department HAVING COUNT(*) > 82 ORDER BY UserCount DESC LIMIT 0,100
-- 连表查询/多表查询,包括两表查询、三表查询、四表及以上查询
SELECT * FROM Def_Department a INNER JOIN Def_UserDepartment b ON a.DepartmentID=b.DepartmentID WHERE ClientID = 1000
-- 连表查询通过部门分组
SELECT a.Department,COUNT(*) AS UserCount FROM Def_Department a INNER JOIN Def_UserDepartment b ON a.DepartmentID=b.DepartmentID WHERE ClientID = 1000 GROUP BY a.Department
-- 连表查询通过部门分组后筛选条件(行数大于1)
SELECT a.Department,COUNT(*) AS UserCount FROM Def_Department a INNER JOIN Def_UserDepartment b ON a.DepartmentID=b.DepartmentID WHERE ClientID = 1000 GROUP BY a.Department HAVING COUNT(*) > 1
-- 连表查询通过部门分组后筛选条件(行数大于1)再通过条件进行排序(通过行数排序,默认asc升序),备注:HAVING不能引用别名,只能用字段名或者COUNT(*)等聚合函数,ORDER BY既可以用别名,也可以用字段名或者COUNT(*)等聚合函数
SELECT a.Department,COUNT(*) AS UserCount FROM Def_Department a INNER JOIN Def_UserDepartment b ON a.DepartmentID=b.DepartmentID WHERE ClientID = 1000 GROUP BY a.Department HAVING COUNT(*) > 1 ORDER BY UserCount DESC
-- 限制,取前10条记录
SELECT a.Department,COUNT(*) AS UserCount FROM Def_Department a INNER JOIN Def_UserDepartment b ON a.DepartmentID=b.DepartmentID WHERE ClientID = 1000 GROUP BY a.Department HAVING COUNT(*) > 1 ORDER BY UserCount DESC LIMIT 10
-- 分页,跳过第0条,从第1条开始取,取100条记录
SELECT a.Department,COUNT(*) AS UserCount FROM Def_Department a INNER JOIN Def_UserDepartment b ON a.DepartmentID=b.DepartmentID WHERE ClientID = 1000 GROUP BY a.Department HAVING COUNT(*) > 1 ORDER BY UserCount DESC LIMIT 0,100
-- 两表查询,就是把两表的字段连起来查询
SELECT * FROM Def_Department a INNER JOIN Def_UserDepartment b ON a.DepartmentID=b.DepartmentID
-- 三表查询,就是把三表的字段连起来查询
SELECT * FROM Def_Department a INNER JOIN Def_UserDepartment b ON a.DepartmentID=b.DepartmentID INNER JOIN Def_User c ON b.UserID=c.UserID
四、备注:
在SQL中,连表查询(JOIN)是多表查询的常用方式,它允许你将来自两个或多个表的行结合起来,基于它们之间共同拥有的列。这里有几种常见的JOIN类型:
1、INNER JOIN:返回两个表中存在匹配的行。
2、LEFT JOIN(或 LEFT OUTER JOIN):返回左表的所有行,即使右表中没有匹配。
3、RIGHT JOIN(或 RIGHT OUTER JOIN):返回右表的所有行,即使左表中没有匹配。
4、FULL JOIN(或 FULL OUTER JOIN):返回左表和右表中所有的行。