常见表关系
秘诀:从一头出发,所在位置不同,得到的结果也不同
1.一对一 例子:一个老公对应一个老婆,一个员工对应一个部门
2.一对多 例子:一个部门对应多个原
3.多对多 例子:一个学生对应多个老师,一个老师对应多个学生
一个角色对应多个权限,一个权限对应多个角色 多对多其实就是双向的一对多
4.多对一 实质:站在一头出发,所以就是一对一
Mybatis中映射规则:结果集中不允许出现重名字段
@Data
@Accessors(chain = true)
@NoArgsConstructor
@AllArgsConstructor
public class Emp implements Serializable {
private Integer empId;
private String empName;
//关联关系 1: 一个员工对应一个部门
private Dept dept;
}
@Data
@Accessors(chain = true)
@NoArgsConstructor
@AllArgsConstructor
public class Dept implements Serializable {
private Integer deptId;
private String deptName;
//一个部门对应多个员工
private List emps;
}
需求:进行一对一查询,一个员工对应一个部门(看pojo,不要有疑问)
sql:select * from emp e,dept d where e.dept_id = d.dept_id //一对一关联查询
难点:如何完成一对一的封装
固定用法:association:将结果集封装为单独的对象dept
2.property 需要封装的属性名称
3.javaType 固定用法: 属性的类型
下面是完整的代码:findAll()不必多说,就是查的sql中的数据,可以看出dept是包含deptId和deptName的,需要将dept类的两个属性封装为dept对象(实例)中
select e.emp_id,e.emp_name,d.dept_id,d.dept_name from emp e,dept d where e.dept_id = d.dept_id //映射主键,xml中不可以使用//注释,这里图个快捷
需求:进行一对多查询,一个部门对应多个员工(这里看pojo就知道要封装,不要疑问)
sql:select d.dept_id,d.dept_name,e.emp_id,e.emp_name from dept d,emp e
where d.dept_id = e.emp_id
难点:如何将emp中查到的数据数据封装到集合list
固定用法:collection标签封装集合,在这里表示将同一个部门下得员工封装到一个集合中
property表示要封装成的集合名称
ofType表示元素类型
select d.dept_id,d.dept_name,e.emp_id,e.emp_name from dept d,emp e where d.dept_id=e.emp_id
注意:表有主次之分的,分的主次可以简单很多,Mybatis的封装一般都是一级封装
Mybatis的子查询
矛盾点:1.如果想简化sql,则映射文件肯定复杂 2。如果想简化映射文件,则sql语句复杂
需求:使用子查询来完成封装
子查询本质特点:将多表关联查询,转化为多个单表查询
思考;这个既然要使用子查询的,但是返回值不仅仅是dept一张表的数据(这里和上面一样实现一对多,只是换种方法),所以常规的sql:
select dept_id,dept_name from emp where dept_id in (select dept_id from emp)肯定不可以
最终目的是将emp查询的数据封装List
代码如下:
select * from dept //这里可以写成select dept_id,dept_name from dept, 由于表中没有字段emps, 写在这里报错,就这样写结果也是可以封装的,自己已经验证过,所以遇到当字段只是表中 的一部分但是业务需要封装时,这时就需要将指定的字段写在这里,而不能只写个*就可以 //映射主键 //二次查询,将column="dept_id"字段的值作为参数,传递给子查询//映射其他字段 //数据集合封装
同理,一对一的封装,一个员工对应一个部门的封装代码为:



