mybatis-基於xml的多表查詢


mybatis動態SQL

簡化SQL

Sql 中可將重復的 sql 提取出來,使用時用include 引用即可,最終達到 sql 重用的目的。

<!--    抽取重復片段-->
<sql id="selectAll" >
  select * from user 
</sql>
<!--使用重復片段-->
<select id="findUserAll" resultType="user">
--         select * from user
  <include refid="selectAll"></include>
</select>

標簽:抽取重復SQL片段。id屬性:指定重復片段的名稱。

標簽:引用 抽取的重復片段。refix屬性:該屬性值為 標簽id屬性值。

mybatis多表查詢

一對一查詢

示例:一個gameAccount(游戲賬號)與player(玩家)為一對一關系

實現:

  1. 數據庫中game_account(賬號表)包含player(玩家表)的主鍵作為外鍵。
    • 一的一方的主鍵作為一的一方的外鍵。
  2. 實體類中GameAccount(賬號實體類)包含Player(玩家實體類)的引用。
    • 主表(直接查詢的表)包含從表(關聯查詢的表)實體類的引用。

需求:查詢賬號,並且關聯查詢用戶。

玩家表:

create table player(
	pid int primary key auto_increment,
  pname varchar(20),
  psex varchar(20)
);

賬號表:

create table game_account(
	gid int primary key auto_increment,
  gusername varchar(20),
  gpassword varchar(20),
  gpid int,
  foreign key (gpid) references player(pid)
);

玩家實體類:

package com.mybatis_xml.pojo;
import java.io.Serializable;
public class Player implements Serializable {
  private Integer pid;
  private String pname;
  private String psex;
  //getter,setter,toString
}

賬號實體類:

package com.mybatis_xml.pojo;
import java.io.Serializable;
public class GameAccount implements Serializable {
    private Integer gid;
    private String gusername;
    private String gpassword;
    private Integer gpid;//player表的主鍵
    //一對一關系:主表(直接查詢的表)包含從表(關聯查詢的表)實體類的引用
    private Player player;
    //getter,setter,toString
}

IGameAccountMapper接口:

package com.mybatis_xml.mapper;
import com.mybatis_xml.pojo.GameAccount;
import java.util.List;

public interface IGameAccountMapper {
    //賬號和玩家為一對一關系;查詢賬號,關聯查詢玩家
    List<GameAccount> findAll();
}

IGameAccountMapper.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="com.mybatis_xml.mapper.IGameAccountMapper">
<!-- resultMap標簽用於指定數據庫表與實體的一一映射關系
    id屬性:給定一個唯一標識,是給select標簽resultMap屬性引用的。
    type屬性:接口對應的實體類的全限定類名或者配置了別名后的別名
-->
    <resultMap id="gameAccountMap" type="gameAccount">
<!--id標簽用於指定主鍵對應
    property屬性:用於指定實體類屬性名稱
    column屬性:用於指定數據庫列名
-->
        <id property="gid" column="gid"></id>
<!--result標簽指定非主鍵對應-->
        <result column="gusername" property="gusername"></result>
        <result column="gpassword" property="gpassword"></result>
        <result column="gpid" property="gpid"></result>
<!--association標簽配置GameAccount對象中player對象引用的映射關系:一般為一對一配置
    property屬性:用於指定被引用實體類屬性名稱
    javaType屬性:用於指定被引用實體的Java類全限定類名
-->
        <association property="player" javaType="player">
            <id property="pid" column="pid"></id>
            <result property="pname" column="pname"></result>
            <result property="psex" column="psex"></result>
        </association>
    </resultMap>
<!--
SELECT
  p.*,g.gid,g.gpid,g.gpassword,g.gusername
FROM
  game_account g,
  player p
WHERE
  g.gpid = p.pid
-->
<!--
SELECT 查詢的字段
FROM 表 表別名
-->
    <select id="findAll" resultMap="gameAccountMap">
        SELECT
            p.*,g.gid,g.gpid,g.gpassword,g.gusername
        FROM
            game_account g,
            player p
        WHERE
            g.gpid = p.pid
    </select>
</mapper>

OneToOne.class測試類:

import com.mybatis_xml.mapper.IGameAccountMapper;
import com.mybatis_xml.pojo.GameAccount;
import org.apache.ibatis.io.Resources;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.apache.ibatis.session.SqlSessionFactoryBuilder;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import java.io.IOException;
import java.io.InputStream;
import java.util.List;

public class OneToOne {
    private InputStream is;
    private SqlSession session;
    private SqlSessionFactoryBuilder sqlSessionFactoryBuilder;
    private SqlSessionFactory factory;
    private IGameAccountMapper gameAccountMapper;

    @Before
    public void init() throws IOException {
        String resource = "mybatis-config.xml";
        // 讀取mybatis配置文件
        is = Resources.getResourceAsStream(resource);
        // 創建構造者對象
        sqlSessionFactoryBuilder = new SqlSessionFactoryBuilder();
        // 創建工廠對象
        factory = sqlSessionFactoryBuilder.build(is);
        // 創建SqlSession對象
        session = factory.openSession();
        // 創建IUserMapper對象
        gameAccountMapper = session.getMapper(IGameAccountMapper.class);
    }
    @After
    public void destory() throws IOException {
        session.close();
        is.close();
    }

    //測試查詢所有
    @Test
    public void testFindAll() throws IOException {
        List<GameAccount> pgs = gameAccountMapper.findAll();
        System.out.println(pgs);
    }
}

多對一查詢

示例:一個Book(書籍)與Own(所有者)為多對一關系。

實現:

  1. 數據庫中book(書籍表)包含own(所有者表)的主鍵作為外鍵。
    • 把一的一方的主鍵作為多的一方的外鍵。
  2. 實體類中Own(所有者實體類)包含Book(書籍實體類)的集合引用。
    • 主表(直接查詢的表)實體類包含從表(關聯查詢的表)實體類集合的引用。

需求:查尋所有者,並且關聯查詢書籍。

所有者表:

create table own(
	oid int primary key auto_increment,
	oname varchar(20)
);

書籍表:

create table book(
 bid int primary key auto_increment,
 bname varchar(20),
 boid int,
 foreign key(boid) references own(oid)
);

書籍實體類:

package com.mybatis_xml.pojo;
import java.io.Serializable;
public class Book implements Serializable {
    private Integer bid;
    private String bname;
    private Integer boid;
  //getter,setter,toString省略
}

所有者實體類:

package com.mybatis_xml.pojo;
import java.io.Serializable;
import java.util.List;
public class Own implements Serializable {
    private Integer oid;
    private String oname;
    //多對一:主表包含從表的集合引用
    private List<Book> books;
  //getter,setter,toString省略
}

IOwnMapper接口:

package com.mybatis_xml.mapper;
import com.mybatis_xml.pojo.Own;
import java.util.List;
public interface IOwnMapper {
  //所有者與書籍為一對多關系:查詢所有者,關聯查詢書籍
    List<Own> findAll();
}

IOwnMapper.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="com.mybatis_xml.mapper.IOwnMapper">
    <resultMap id="ownMap" type="own">
        <id column="oid" property="oid"></id>
        <result column="oname" property="oname"></result>
<!--collection標簽配置own對象中Book集合的映射關系:一般為一對多配置
    property屬性:指定集合變量名稱
    ofType屬性:指定集合元素類型,全限定類名
-->
        <collection property="books" ofType="book">
            <id property="bid" column="bid"></id>
            <result property="bname" column="bname"></result>
            <result property="boid" column="boid"></result>
        </collection>
    </resultMap>

    <select id="findAll" resultMap="ownMap">
        select
               o.*,b.bid,b.boid,b.bname
        from own o
            left outer
                join book b
                    on b.boid = o.oid;
    </select>
</mapper>

ManyToOne.class測試類:

import com.mybatis_xml.mapper.IOwnMapper;
import com.mybatis_xml.pojo.Own;
import org.apache.ibatis.io.Resources;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.apache.ibatis.session.SqlSessionFactoryBuilder;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;

import java.io.IOException;
import java.io.InputStream;
import java.util.List;

public class ManyToOne {

    private InputStream is;
    private SqlSession session;
    private SqlSessionFactoryBuilder sqlSessionFactoryBuilder;
    private SqlSessionFactory factory;
    private IOwnMapper ownMapper;

    @Before
    public void init() throws IOException {
        String resource = "mybatis-config.xml";
        // 讀取mybatis配置文件
        is = Resources.getResourceAsStream(resource);
        // 創建構造者對象
        sqlSessionFactoryBuilder = new SqlSessionFactoryBuilder();
        // 創建工廠對象
        factory = sqlSessionFactoryBuilder.build(is);
        // 創建SqlSession對象
        session = factory.openSession();
        // 創建IUserMapper對象
        ownMapper = session.getMapper(IOwnMapper.class);
    }
    @After
    public void destory() throws IOException {
        session.close();
        is.close();
    }

    //測試查詢所有
    @Test
    public void testFindAll() throws IOException {
        List<Own> pgs = ownMapper.findAll();
        System.out.println(pgs);
    }
}

多對多查詢

示例:一個Student(學生)對應多個(Teacher)老師,一個 、Teacher(老師)對應多個Student(學生),所以學生和老師是多對多關系。

實現:

  • 數據庫中student(學生表)的主鍵,teacher(老師表)的主鍵,作為s_t(學生_老師表)的外鍵。
    • 抽取兩個主鍵,作為新的表的外鍵
  • 實體類中Student(學生實體類)引用Teacher(老師實體類)的集合,Teacher(老師實體類)引用Student(學生實體類)的集合。
    • 主從表各包含對對方實體集合的引用

student表:

create table student(
 sid int primary key auto_increment,
 sname varchar(20)
);

teacher表:

create table teacher(
	tid int primary key auto_increment,
	tname varchar(20)
);

中間表:

-- 注意:st_sid需要添加括號
create table st(
	st_sid int,
	st_tid int,
	foreign key (st_sid) references student(sid),
	foreign key (st_tid) references teacher(tid)
);

Teacher實體類:

package com.mybatis_xml.pojo;
import java.io.Serializable;
import java.util.List;

public class Teacher implements Serializable {
    private Integer tid;
    private String tname;
    //多對多:主表和從表各包含對方集合的引用
    private List<Student> students;
    //setter,getter,toString省略
}

Student實體類:

package com.mybatis_xml.pojo;
import java.io.Serializable;
import java.util.List;

public class Student implements Serializable {
    private Integer sid;
    private String sname;
    //多對多:主表和從表各包含對方集合的引用
    private List<Teacher> teachers;
    //setter,getter,toString省略
}

IStudentMapper接口:

package com.mybatis_xml.mapper;
import com.mybatis_xml.pojo.Student;
import java.util.List;
public interface IStudentMapper {
    //多對多:查詢學生,關聯查詢老師
    List<Student> findAll();
}

ITeacherMappper接口:

package com.mybatis_xml.mapper;
import com.mybatis_xml.pojo.Teacher;
import java.util.List;
public interface ITeacherMapper {
    //多對多:查詢老師,關聯查詢學生
    List<Teacher> findAll();
}

IStudentMapper.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="com.mybatis_xml.mapper.IStudentMapper">
    <resultMap id="studentMap" type="student">
        <id property="sid" column="sid"></id>
        <result property="sname" column="sname"></result>
        <collection property="teachers" ofType="teacher">
            <id property="tid" column="tid"></id>
            <result property="tname" column="tname"></result>
        </collection>
    </resultMap>

    <select id="findAll" resultMap="studentMap">
        select s.*,t.*
        from student s
        left outer join st on s.sid=st.st_sid
        left outer join teacher t on t.tid=st.st_tid
    </select>
</mapper>

ITeacherMapper.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="com.mybatis_xml.mapper.ITeacherMapper">
    <resultMap id="teacherMap" type="teacher">
        <id property="tid" column="tid"></id>
        <result property="tname" column="tname"></result>
        <collection property="students" ofType="student">
            <id property="sid" column="sid"></id>
            <result property="sname" column="sname"></result>
        </collection>
    </resultMap>

    <select id="findAll" resultMap="teacherMap">
        select t.*,s.*
        from student s
                 left outer join st on s.sid=st.st_sid
                 left outer join teacher t on t.tid=st.st_tid
    </select>
</mapper>

ManyToMany.class測試類:

import com.mybatis_xml.mapper.IOwnMapper;
import com.mybatis_xml.mapper.IStudentMapper;
import com.mybatis_xml.mapper.ITeacherMapper;
import com.mybatis_xml.pojo.Student;
import com.mybatis_xml.pojo.Teacher;
import org.apache.ibatis.io.Resources;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.apache.ibatis.session.SqlSessionFactoryBuilder;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;

import java.io.IOException;
import java.io.InputStream;
import java.util.List;

public class ManyToMany {
    private InputStream is;
    private SqlSession session;
    private SqlSessionFactoryBuilder sqlSessionFactoryBuilder;
    private SqlSessionFactory factory;
    private IStudentMapper studentMapper;
    private ITeacherMapper teacherMapper;

    @Before
    public void init() throws IOException {
        String resource = "mybatis-config.xml";
        // 讀取mybatis配置文件
        is = Resources.getResourceAsStream(resource);
        // 創建構造者對象
        sqlSessionFactoryBuilder = new SqlSessionFactoryBuilder();
        // 創建工廠對象
        factory = sqlSessionFactoryBuilder.build(is);
        // 創建SqlSession對象
        session = factory.openSession();
        // 創建IUserMapper對象
        studentMapper = session.getMapper(IStudentMapper.class);
        teacherMapper = session.getMapper(ITeacherMapper.class);
    }
    @After
    public void destory() throws IOException {
        session.close();
        is.close();
    }

    @Test
    public void testFindAllStudent(){
        List<Student> students = studentMapper.findAll();
        System.out.println(students);
    }

    @Test
    public void testFindAllTeacher(){
        List<Teacher> teachers = teacherMapper.findAll();
        System.out.println(teachers);
    }
}


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2026 CODEPRJ.COM