前面我们讲解了Join的底层驱动表 选择原理,也知道了基本的内连接外连接两种SQL查询表连接方式
但是我们再查询多表的时候on和where语句到底有什么区别?
下面我们来实战SQL演练一下
我们先创建两个表 test_user 和 test_order 这两个表作为我们的测试表及测试数据
#创建test_user
CREATE TABLE `test_user` (
`id` bigint NOT NULL AUTO_INCREMENT COMMENT '主键',
`user_name` char(32) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '用户名字',
`age` int DEFAULT NULL COMMENT '年龄',
PRIMARY KEY (`id`),
KEY `idx_age` (`age`),
KEY `idx_name` (`user_name`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci COMMENT='用户表';
#创建表 test_order
CREATE TABLE `test_order` (
`id` int NOT NULL AUTO_INCREMENT,
`user_id` int NOT NULL COMMENT '用户id,就是test_user的唯一主键id',
`order_name` varchar(32) NOT NULL DEFAULT '订单信息',
`pay` int NOT NULL DEFAULT '0',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci COMMENT='订单表';
插入数据
#插入 user 用户数据
INSERT INTO `prepare`.`test_user` (`id`, `user_name`, `age`) VALUES (1, 'aa', 10);
INSERT INTO `prepare`.`test_user` (`id`, `user_name`, `age`) VALUES (2, 'bb', 20);
INSERT INTO `prepare`.`test_user` (`id`, `user_name`, `age`) VALUES (3, 'cc', 30);
INSERT INTO `prepare`.`test_user` (`id`, `user_name`, `age`) VALUES (4, 'dd', 40);
#插入 order 订单数据
INSERT INTO `prepare`.`test_order` (`id`, `user_id`, `order_name`, `pay`) VALUES (1, 1,'衣服', 100);
INSERT INTO `prepare`.`test_order` (`id`, `user_id`, `order_name`, `pay`) VALUES (2, 2,'鞋子', 200);
INSERT INTO `prepare`.`test_order` (`id`, `user_id`, `order_name`, `pay`) VALUES (3, 2,'电视', 300);
根据表记录 可以知道
当连接条件是 inner join内连接时, on连接的过滤条件 等同于 where 过滤条件
也就是说 你把过滤条件 放到 on 语句后面 或者放到 where 语句后面,效果是一致的
#on语句过滤条件
select * from test_user inner join test_order on test_user.id = test_order.user_id;
#where语句作为过滤条件
select * from test_user inner join test_order where test_user.id = test_order.user_id;
left join外连接的时候, on 连接条件过滤 和 where 条件过滤 区别就很大了, on 条件是 被驱动表 不匹配的也要展示, 用NULL来填充
但是 where语句就是 不满足的全部都过滤掉, 下面我们来实际看下效果
#找出驱动表
explain select * from test_user left join test_order on ( test_user.id = test_order.user_id) and test_order.user_id = 2;
#查询结果
select * from test_user left join test_order on ( test_user.id = test_order.user_id) and test_order.user_id = 2;
查看结果
前面我们看到了 用 on 去 连接两个表, 并且设置了 test_order.user_id = 2
但是返回结果 并不是 user_id = 2的数据, 而是 不匹配的数据用NULL来代替了
如果是 where 语句呢?
如果说 test_order.user_id = 2 挂在where语句后面 效果是什么样子呢?
#查看驱动表
explain
select * from test_user left join test_order on ( test_user.id = test_order.user_id) where test_order.user_id = 2;
#执行查询语句
select * from test_user left join test_order on ( test_user.id = test_order.user_id) where test_order.user_id = 2;
查看执行结果
如果 上面的例子 你还是没区分出来 on 和 where的 区别, 我们再来一个更加直观的, 一眼就看出来区别
#on 条件
select * from test_user left join test_order on test_user.id = test_order.user_id and test_order.pay > 100;
#where 条件
select * from test_user left join test_order on test_user.id = test_order.user_id where test_order.pay > 100;
我们看下执行结果
至此,我们已经彻底分清楚了 on语句和where语句的区别, 这对于我们能够正确的处理业务,十分重要