MyBatis(四)关于多表联查 关联关系

在MyBatis中,进行多表联查时关联关系主要有这几种:一对多,多对一,多对多,还有一种自关联这几种用的比较多

1.一对多:有两种方式

(1)用一条sql语句进行查询    (以查询部门和员工为案例)

 首先创建实体类

package entity;

import java.util.List;

/**
 * Created by mycom on 2018/2/26.
 */
public class Dept {//部门
    private Integer deptNo;

    private String deptName;

    private List<Emp> emps;

    public List<Emp> getEmps() {
        return emps;
    }

    public void setEmps(List<Emp> emps) {
        this.emps = emps;
    }

    public Integer getDeptNo() {
        return deptNo;
    }

    public void setDeptNo(Integer deptNo) {
        this.deptNo = deptNo;
    }

    public String getDeptName() {
        return deptName;
    }

    public void setDeptName(String deptName) {
        this.deptName = deptName;
    }



}

然后创建部门接口以及对应的xml文件

package dao;

import entity.Dept;
import entity.Emp;

import java.util.List;

/**
 * Created by mycom on 2018/2/26.
 */
public interface IDeptDao {
    //根据部门编号获得部门名称  员工名称  单条sql
    public Dept getEmpByDeptNo(int deptNo);
}



<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper
        PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="dao.IDeptDao">
    <resultMap id="deptMaper" type="Dept">
        <id column="d" property="deptNo"></id>
        <result column="deptName" property="deptName"></result>
        <collection property="emps" ofType="Emp">
            <id column="empNo" property="empNo"></id>
            <result column="empName" property="empName"></result>
        </collection>
    </resultMap>

    <!--查询部门和员工  单条sql语句方案-->
    <select id="getEmpByDeptNo" resultMap="deptMaper">
        SELECT dept.deptNo as d ,deptName,empName FROM dept,emp
        WHERE dept.`deptNo`=emp.`deptNo`
        AND dept.`deptNo`=#{deptNo}
    </select>

</mapper>

编写测试类
//查询部门和员工  单条sql
@Test
public void oneToMany(){
    SqlSession sqlSession = MyBatisUtil.getSession();
    IDeptDao mapper = sqlSession.getMapper(IDeptDao.class);
    Dept dept = mapper.getEmpByDeptNo(1);
    System.out.println("部门名称"+dept.getDeptName());
    for (Emp emp:dept.getEmps()) {
        System.out.println(emp.getEmpName());
    }
    sqlSession.close();
}

(2)多条sql语句查询

   
接口中的方法
public interface IDeptDao {
 //根据部门编号获得部门名称  员工名称  多条sql
    public Dept getEmpByDeptNoMultiSQL(int deptNo);
}
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper
        PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="dao.IDeptDao">
    <!--多条sql-->
    <resultMap id="deptMaperMulti" type="Dept">
        <id column="d" property="deptNo"></id>
        <result column="deptName" property="deptName"></result>
        <collection property="emps" ofType="Emp" select="selectEmpByDeotNo" column="deptNo">
        </collection>
    </resultMap>
    <select id="selectEmpByDeotNo" resultType="Emp">
        SELECT * from Emp
        WHERE  deptNo=#{deptNo}
    </select>
    <!--查询部门和员工  多条sql语句方案-->
    <select id="getEmpByDeptNoMultiSQL" resultMap="deptMaperMulti">
        select * from dept
        where deptNo=#{deptNo}
    </select>
</mapper>

 

测试类

    //查询部门和员工  多条sql
    @Test
    public void oneToManyMulti(){
        SqlSession sqlSession = MyBatisUtil.getSession();
        IDeptDao mapper = sqlSession.getMapper(IDeptDao.class);
        Dept dept = mapper.getEmpByDeptNoMultiSQL(1);
        System.out.println("部门名称"+dept.getDeptName());
        for (Emp emp:dept.getEmps()) {
            System.out.println(emp.getEmpName());
        }
        sqlSession.close();
    }

2.多对一(同样有两种方法  单条sql和多条sq)同样使用部门和员工的案例  站在多的一方

首先是接口

package dao;

import entity.Emp;

/**
* Created by mycom on 2018/2/26.
*/
public interface IEmpDao {
//根据员工编号查询 单条sql
public Emp getDeptByEmpNo(int empNo);
//根据员工编号查询 多条sql
public Emp getDeptByEmpNoMulti(int empNo);
}

以及接口对应的xml文件

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper
        PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="dao.IEmpDao">
    <resultMap id="empMaper" type="Emp">
        <id column="empNo" property="empNo"></id>
        <result property="empName" column="empName"></result>
        <association property="dept" javaType="dept">
            <id column="deptNo" property="deptNo"></id>
            <result property="deptName" column="deptName"></result>
        </association>
    </resultMap>
    <resultMap id="empMaperMulti" type="Emp">
        <id column="empNo" property="empNo"></id>
        <result property="empName" column="empName"></result>
        <association property="dept" javaType="dept" select="selectDeptByEmpNo" column="deptNo">
        </association>
    </resultMap>
    <!--查询部门和员工 单条sql语句方案-->
    <select id="getDeptByEmpNo" resultMap="empMaper">
        SELECT * FROM dept,emp
        WHERE dept.`deptNo`=emp.`deptNo`
        AND empNo=#{empNo}
    </select>


    <select id="selectDeptByEmpNo" resultType="Dept">
        SELECT * FROM dept WHERE deptNo=#{deptNo}
    </select>
    <!--查询部门和员工 多条sql语句方案-->
    <select id="getDeptByEmpNoMulti" resultMap="empMaperMulti">
        SELECT * FROM emp
        WHERE empNo=#{empNo}
    </select>


</mapper>

最后编写测试类进行测试

//多对一  单条sql
    @Test
    public void manyToOne(){
        SqlSession sqlSession = MyBatisUtil.getSession();
        IEmpDao mapper = sqlSession.getMapper(IEmpDao.class);
        Emp emp = mapper.getDeptByEmpNo(1);
        System.out.println("员工名称:"+emp.getEmpName());
        System.out.println("员工所属部门:"+emp.getDept().getDeptName());
        sqlSession.close();
    }
    //多对一  多条sql
    @Test
    public void manyToOneMulti(){
        SqlSession sqlSession = MyBatisUtil.getSession();
        IEmpDao mapper = sqlSession.getMapper(IEmpDao.class);
        Emp emp = mapper.getDeptByEmpNoMulti(1);
        System.out.println("员工名称:"+emp.getEmpName());
        System.out.println("员工所属部门:"+emp.getDept().getDeptName());
        sqlSession.close();
    }

3.多对多(比如一名学生可以由多个老师教,一个老师可以教多个学生)

先编写学生类和老师类

package entity;

/**
 * Created by mycom on 2018/2/26.
 */
public class Student {

    private Integer sid;
    private String sname;

    public Integer getSid() {
        return sid;
    }

    public void setSid(Integer sid) {
        this.sid = sid;
    }

    public String getSname() {
        return sname;
    }

    public void setSname(String sname) {
        this.sname = sname;
    }
}



//老师类
package entity;

import java.util.ArrayList;
import java.util.List;

/**
* Created by mycom on 2018/2/26.
*/
public class Teacher {
private Integer tid;
private String tname;

public Integer getTid() {
return tid;
}

public void setTid(Integer tid) {
this.tid = tid;
}

public String getTname() {
return tname;
}

public void setTname(String tname) {
this.tname = tname;
}

public List<Student> getStus() {
return stus;
}

public void setStus(List<Student> stus) {
this.stus = stus;
}

//植入学生集合
private List<Student> stus=new ArrayList<Student>();

}


接口中方法和xml文件

package dao;

import entity.Student;
import entity.Teacher;

import java.util.List;

/**
 * Created by mycom on 2018/2/26.
 */
public interface ITeacherDao {
    //根据老师编号查询学生集合
    public Teacher findAllStudentsByTid(int tid);
}
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper
        PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="dao.ITeacherDao">
    <resultMap id="teacherMaper" type="Teacher">
        <id column="tid" property="tid"></id>
        <result column="tname" property="tname"></result>
        <collection property="stus" ofType="Student">
            <id column="sid" property="sid"></id>
            <result column="sname" property="sname"></result>
        </collection>
    </resultMap>
    <!--根据老师编号查询学生集合-->
    <select id="findAllStudentsByTid" resultMap="teacherMaper">
        SELECT * FROM student AS s,teacher AS t ,Teacher_Student AS ts
        WHERE  s.`sid`=ts.`sid`
        AND t.`tid`=ts.`tid`
        AND t.`tid`=#{tid}
    </select>


</mapper>

测试类

//多对多
    @Test
    public void manyToMany(){
        SqlSession sqlSession = MyBatisUtil.getSession();
        ITeacherDao mapper = sqlSession.getMapper(ITeacherDao.class);
        Teacher teacher = mapper.findAllStudentsByTid(1);
        System.out.println("名老师姓:"+teacher.getTname());
        for (Student student:teacher.getStus()) {
            System.out.println(student.getSname());
        }
        sqlSession.close();
    }

4.自关联(自己即充当一的一方,又可以充当多的一方)

比如无限极分类

首先看数据库中category表

pid为0的是一级分类

pid为1的是二级分类

pid为3的是三级分类

那么category既充当了一又充当了多

现在开始编写实体类Category

package entity;

import java.util.List;

/**
 * Created by mycom on 2018/2/26.
 */
public class Category {
    private Integer cid;
    private String cname;
    private List<Category> cates;

    @Override
    public String toString() {
        return "Category{" +
                "cid=" + cid +
                ", cname='" + cname + '\'' +
                ", cates=" + cates +
                '}';
    }

    public Integer getCid() {
        return cid;
    }

    public void setCid(Integer cid) {
        this.cid = cid;
    }

    public String getCname() {
        return cname;
    }

    public void setCname(String cname) {
        this.cname = cname;
    }

    public List<Category> getCates() {
        return cates;
    }

    public void setCates(List<Category> cates) {
        this.cates = cates;
    }
}

接口

package dao;

import entity.Category;

import java.util.List;

/**
 * Created by mycom on 2018/2/26.
 */
public interface ICategoryDao {
    //根据pid查询分类
    public List<Category> getChildrenByPid(int pid);
}
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="dao.ICategoryDao">
<resultMap id="categoryMapper" type="Category">
<id column="cid" property="cid"></id>
<result column="cname" property="cname"></result>
<!--直到下一级没有东西了就停止,否则就继续线下一层找-->
<collection property="cates" ofType="Category" select="getChildrenByPid" column="cid"></collection>
</resultMap>
<select id="getChildrenByPid" resultMap="categoryMapper">
select * from category where pid=#{pid}
</select>
</mapper>

测试类

//自关联
    @Test
    public void selfSelect(){
        SqlSession sqlSession = MyBatisUtil.getSession();
        ICategoryDao mapper = sqlSession.getMapper(ICategoryDao.class);
        List<Category> list = mapper.getChildrenByPid(1);
        for (Category category:list) {
            System.out.println(category);
        }
        sqlSession.close();
    }

 

posted @ 2018-02-26 22:12  明渃筱曦  阅读(461)  评论(0编辑  收藏  举报