MySql表联查 JOIN查询[INNER JOIN、LEFT JOIN、RIGHT JOIN] 原创

---------------------------------
---------------------------------

-- 表联查

---------------------------------
---------------------------------

-- CREATE TABLE `user_types` (
--   `id` int NOT NULL AUTO_INCREMENT,
--   `title` varchar(20) NOT NULL DEFAULT '' COMMENT '类型名称',
--   `status` tinyint(1) NOT NULL DEFAULT '0' COMMENT '状态',
--   PRIMARY KEY (`id`)
-- ) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=utf8mb3 COMMENT='用户类型表';

-- CREATE TABLE `users` (
--   `id` int unsigned NOT NULL AUTO_INCREMENT,
--   `username` varchar(20) DEFAULT NULL,
--   `status` tinyint(1) DEFAULT '0',
--   `create_time` int NOT NULL DEFAULT '0',
--   `integral` int DEFAULT '0' COMMENT '积分',
--   `type_id` int NOT NULL,
--   PRIMARY KEY (`id`),
--   KEY `fk_user_type` (`type_id`),
--   CONSTRAINT `fk_user_type` FOREIGN KEY (`type_id`) REFERENCES `user_types` (`id`)
-- ) ENGINE=InnoDB AUTO_INCREMENT=15 DEFAULT CHARSET=utf8mb3 COMMENT='用户表';

-- CREATE TABLE `orders` (
--   `id` bigint unsigned NOT NULL AUTO_INCREMENT COMMENT '订单主键',
--   `user_id` int unsigned NOT NULL DEFAULT '0' COMMENT '用户主键ID',
--   `goods_id` int unsigned NOT NULL DEFAULT '0' COMMENT '商品主键ID',
--   `amount` int unsigned NOT NULL DEFAULT '0' COMMENT '订单价格[单位:分]',
--   `pay_amount` int unsigned NOT NULL DEFAULT '0' COMMENT '订单实际支付金额[单位:分]',
--   `status` tinyint unsigned NOT NULL DEFAULT '1' COMMENT '订单状态:1 未支付 2 已支付 3 已退款 4 已评价 5 已取消',
--   `pay_time` int unsigned NOT NULL DEFAULT '0' COMMENT '订单支付时间',
--   `create_time` int unsigned NOT NULL DEFAULT '0' COMMENT '订单创建时间',
--   PRIMARY KEY (`id`),
--   KEY `user_id` (`user_id`),
--   KEY `status` (`status`)
-- ) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8mb3 COMMENT='用户订单表';



-- 多表联查的理论依据:笛卡尔积
-- 通过笛卡尔乘积,把两个或者多个表变为一个大表,里面包含了有效的,无效的记录(需要加条件进行过滤数据)
-- 1、多表联合查询,你想要的数据在多个表中,得从多个表中查询获取,但是必须添加条件过滤,
--   如果不加条件,会出现大量错误数据。
-- 2、条件,连接条件:先分析表跟表之间的关系,分析数据和数据之间的关系,把关系写成 SQL 语句:
--    多数情况下,表和表之间的关系是主外键关系,但是有特殊,有例外。
-- 3、一个连接条件,只能连2个表,如果要连接N个表,至少需要 N-1 个连接条件;

-- 表联查分为3中 内连接,左连接,右连接
-- INNER JOIN 内连接 左表和右表通过连接[ON]条件能够连接上的才会查出来。
-- LEFT JOIN 左连接 将左表的内容全部显示,不管右表是否有对应的记录;
-- RIGHT JOIN 右连接 将右表的内容全部显示,不管左表是否有对应的记录。


-- INNER JOIN
-- 当orders表中user_id的值存在于users表中才能查出数据
-- insert into orders(id, user_id, goods_id, amount, pay_amount, status, pay_time, create_time) values(1, 1, 1, 100, 100, 2, 1677142358, 1677122358);
SELECT users.*,orders.id as order_id,orders.goods_id FROM users INNER JOIN orders ON users.id=orders.user_id; -- 查出一条数据
SELECT users.*,orders.id as order_id,orders.goods_id FROM users INNER JOIN orders ON users.id=orders.user_id WHERE users.id = 2; -- 查不出数据


-- 两条结果查出的数据一致,inner join并不以谁为基础,它只显示符合条件的记录
select users.`id` as user_id,users.type_id,users.username,user_types.* from users inner join user_types on users.type_id = user_types.id;
select users.`id` as user_id,users.type_id,users.username,user_types.* from user_types inner join users on users.type_id = user_types.id;
-- +---------+---------+--------------+----+--------+--------+
-- | user_id | type_id | username     | id | title  | status |
-- +---------+---------+--------------+----+--------+--------+
-- |       1 |       1 | 张三         |  1 | 呵呵   |      1 |
-- |       2 |       1 | 测试         |  1 | 呵呵   |      1 |
-- |       3 |       1 | Hello       |  1 | 呵呵   |      1 |
-- |       4 |       1 | 王二         |  1 | 呵呵   |      1 |
-- |       5 |       1 | HAHA        |  1 | 呵呵   |      1 |
-- |       6 |       1 | WORLD       |  1 | 呵呵   |      1 |
-- |       7 |       1 | 章三2        |  1 | 呵呵   |      1 |
-- |       8 |       1 | 测试你好      |  1 | 呵呵   |      1 |
-- |       9 |       1 | Yesterday    |  1 | 呵呵   |      1 |
-- |      10 |       1 | CCCCCCC      |  1 | 呵呵   |      1 |
-- |      11 |       1 | AAAAA        |  1 | 呵呵   |      1 |
-- |      12 |       1 | BBBBB        |  1 | 呵呵   |      1 |
-- |      13 |       1 | NULL         |  1 | 呵呵   |      1 |
-- |      14 |       1 | HHHHHH       |  1 | 呵呵   |      1 |
-- +---------+---------+--------------+----+--------+--------+


-- LEFT JOIN
-- 将左表的内容全部显示,不管右表是否有对应的记录
-- 如果右表加了搜索条件之后orders表数据为空,那整个查询的结果就是空,不会变成上一条说明的结果[字段值NULL]
SELECT users.`id`, users.username,orders.user_id,orders.goods_id from users LEFT JOIN orders on users.id = orders.user_id;
SELECT users.`id`, users.username,orders.user_id,orders.goods_id from users LEFT JOIN orders on users.id = orders.user_id WHERE orders.goods_id = 2; -- 查不出数据

-- RIGHT JOIN
-- 将右表的内容全部显示,不管左表是否有对应的记录

insert into user_types (id, title, status) values(2, 'ssss', 1),(3, 'aaaaa', 2);
select user_types.*, users.id as user_id from user_types right join users on users.type_id=user_types.id;
select user_types.*, users.id as user_id from users right join user_types on users.type_id=user_types.id;




posted @ 2023-02-24 15:15  mailfor  阅读(0)  评论(0编辑  收藏  举报  来源