Mybatis一对一 关联查询

Mybatis一对一 关联查询

一、单向

实际开发过程中,经常存在一对一关系,比如一个人只能有一个身份证,一个身份证只能给一个人使用,这就是一对一的关系。

 

一对一关系推荐使用唯一主外键关联,即两张表使用外键关联关系,由于是一对一关联,因此还需要给外键增加unique唯一约束

1.数据库设计

创建身份证表tb_card个人信息表 tb_person

其中:tb_card表中的id为主键,tb_person表中的card_id为外键,并设unique唯一约束

创建身份证表

create table tb_card(

cid int primary key auto_increment,           #卡号id

ccode varchar(18)                             #卡号

);
创建个人信息表

create table tb_person(

pid int primary key auto_increment,                    #个人信息id

pname varchar(50),                                                  #个人信息姓名

psex varchar(4),                                                         #个人信息性别

page int,                                                                       #个人信息年龄

card_id int UNIQUE,                                                  #个人信息卡号

CONSTRAINT fk_id FOREIGN KEY(card_id) REFERENCES tb_card(cid)

);

2.实体类及接口

2.1 在com.liuYongQi.MyBatis4.pojo包中创建Card类和Person类,分别映射tb_card表和tb_person表。

package com.liuYongQi.MyBatis4.pojo;

import java.io.Serializable;

/**
 * @ClassName: Card
 * @Description: 身份证tb_card实体类
 * @Author: Administrator
 * @CreateDate: 2018/10/2 20:29
 * @UpdateUser: Administrator
 * @UpdateDate: 2018/10/2 20:29
 * @UpdateRemark: 修改内容
 * @Version: 1.0
 */

public class Card implements Serializable {
    private Integer cid;    //卡号id

    private String ccode;   //卡号

    public Integer getCid() {
        return cid;
    }

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

    public String getCcode() {
        return ccode;
    }

    public void setCcode(String ccode) {
        this.ccode = ccode;
    }

    public Card(Integer cid, String ccode) {
        this.cid = cid;
        this.ccode = ccode;
    }

    public Card(String ccode) {
        this.ccode = ccode;
    }

    public Card() {
    }

    @Override
    public String toString() {
        return "Card{" +
                "cid=" + cid +
                ", ccode='" + ccode + '\'' +
                '}';
    }
}

package com.liuYongQi.MyBatis4.pojo;

import java.io.Serializable;

/**
 * @ClassName: Person
 * @Description: 个人信息表tb_person实体类
 * @Author: Administrator
 * @CreateDate: 2018/10/2 20:42
 * @UpdateUser: Administrator
 * @UpdateDate: 2018/10/2 20:42
 * @UpdateRemark: 修改内容
 * @Version: 1.0
 */

public class Person implements Serializable {
    private Integer pid;        //个人信息id
    private String pname;       //个人信息姓名
    private String  psex;       //个人信息性别
    private Integer  page;      //个人信息年龄
    private Integer  card_id;   //个人信息卡号
    private Card card;          //人和身份证是一对一的关系,即一个人只有一个身份证

    public Person(Integer pid, String pname, String psex, Integer page, Card card) {
        this.pid = pid;
        this.pname = pname;
        this.psex = psex;
        this.page = page;
        this.card = card;
    }

    public Person() {
    }

    public Integer getPid() {
        return pid;
    }

    public void setPid(Integer pid) {
        this.pid = pid;
    }

    public String getPname() {
        return pname;
    }

    public void setPname(String pname) {
        this.pname = pname;
    }

    public String getPsex() {
        return psex;
    }

    public void setPsex(String psex) {
        this.psex = psex;
    }

    public Integer getPage() {
        return page;
    }

    public void setPage(Integer page) {
        this.page = page;
    }

    public Card getCard() {
        return card;
    }

    public void setCard(Card card) {
        this.card = card;
    }

    public Integer getCard_id() {
        return card_id;
    }

    public void setCard_id(Integer card_id) {
        this.card_id = card_id;
    }

    @Override
    public String toString() {
        return "Person{" +
                "pid=" + pid +
                ", pname='" + pname + '\'' +
                ", psex='" + psex + '\'' +
                ", page=" + page +
                ", card_id=" + card_id +
                ", card=" + card +
                '}';
    }
}

2.2 在com.liuYongQi.MyBatis4.dao中分别创建Card类和Person类的接口(做接口注册)

package com.liuYongQi.MyBatis4.dao;

import com.liuYongQi.MyBatis4.pojo.Card;

/**
 * @ClassName: ICardDao
 * @Description: 身份证tb_card实体类接口
 * @Author: Administrator
 * @CreateDate: 2018/10/2 20:56
 * @UpdateUser: Administrator
 * @UpdateDate: 2018/10/2 20:56
 * @UpdateRemark: 修改内容
 * @Version: 1.0
 */
public interface ICardDao {
    /**
     * @Author Administrator
     * @Description 根据卡号id查询卡号对象
     * @Date 20:57 2018/10/2
     * @Param [cid]
     * @return com.liuYongQi.MyBatis4.pojo.Card
     * @exception
     */
    public Card selectCardByCid(int cid);
}
package com.liuYongQi.MyBatis4.dao;
import com.liuYongQi.MyBatis4.pojo.Card;
import com.liuYongQi.MyBatis4.pojo.Person;
/**
 * @ClassName: IPersonDao
 * @Description: 个人信息表tb_person实体类接口
 * @Author: Administrator
 * @CreateDate: 2018/10/2 20:58
 * @UpdateUser: Administrator
 * @UpdateDate: 2018/10/2 20:58
 * @UpdateRemark: 修改内容
 * @Version: 1.0
 */
public interface IPersonDao {
    /**
     * @Author Administrator
     * @Description 根据个人id查询个人信息对象
     * @Date 20:59 2018/10/2
     * @Param [pid]
     * @return com.liuYongQi.MyBatis4.pojo.Person
     * @exception
     */
    public Person selectPersonByPid(int pid);
 }

3对象/关系映射文件
     3.1使用嵌套结果映射来处理重复的联合结果的子集:

(1)在com.liuYongQi.MyBatis4.mapper包中创建Card类和Person类对象/关系映射文件。

CardMapper.xml文件:

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//ibatis.apache.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<!--Card接口注册-->
<mapper namespace="com.liuYongQi.MyBatis4.dao.ICardDao">
    <!--根据卡号id查询卡号对象-->
    <select id="selectCardByCid" parameterType="int" resultType="com.liuYongQi.MyBatis4.pojo.Card">
        select * from tb_card where cid=#{cid}
    </select>
</mapper>

 

PersonMapper.xml文件:

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//ibatis.apache.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<!--Person接口注册-->
<mapper namespace="com.liuYongQi.MyBatis4.dao.IPersonDao">
    <!--根据个人id查询个人信息对象,返回结果为resultMap-->
    <select id="selectPersonByPid" parameterType="int" resultMap="personMapper">
        select * from tb_person p , tb_card c where p.card_id=c.cid and pid=#{pid}
    </select>
   
    <!--映射Person对象的resultMap(结果映射集)id需要和何resultMap的id一致-->
    <resultMap id="personMapper" type="com.liuYongQi.MyBatis4.pojo.Person">
        <id property="pid" column="pid"></id>  <!--主键-->
        <result property="pname" column="pname"></result>
        <result property="psex" column="psex"></result>
        <result property="page" column="page"></result>
        <result property="card_id" column="card_id"></result>
        <!--一对一关联映射:association-->
        <association property="card" javaType="com.liuYongQi.MyBatis4.pojo.Card">
            <id property="cid" column="cid"></id>
            <result property="ccode" column="ccode"></result>
        </association>
    </resultMap>
</mapper>

 

 

(2)在MyBatisConfig.xml中配置mapper映射文件

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration
        PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
    <!--1. 配置数据库环境,默认使用development数据库构建环境-->
    <environments default="development">
        <!--配置环境变量-->
        <environment id="development">
            <!--配置事务管理器类别-->
            <transactionManager type="JDBC"></transactionManager>
            <!--配置数据源-->
            <dataSource type="POOLED">
                <property name="driver" value="com.mysql.jdbc.Driver"></property>
                <property name="url" value="jdbc:mysql://127.0.0.1:3306/db_mybatis?useUnicode=true&amp;characterEncoding=UTF-8"></property>
                <property name="username" value="root"></property>
                <property name="password" value="root"></property>
            </dataSource>
        </environment>
    </environments>

    <!--2. 加载映射器:实体类对象/关系映射文件-->
    <mappers>
        <mapper resource="com/liuYongQi/MyBatis4/mapper/CardMapper.xml"></mapper>
        <mapper resource="com/liuYongQi/MyBatis4/mapper/PersonMapper.xml"></mapper>
    </mappers>

</configuration>

3.2通过执行另外一个SQL映射语句来返回预期的复杂类型

相关属性解释:

    

PersonMapper.xml文件:

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//ibatis.apache.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<!--Person接口注册-->
<mapper namespace="com.liuYongQi.MyBatis4.dao.IPersonDao">
    <!--根据个人id查询个人信息对象,返回结果为resultMap-->
    <select id="selectPersonByPid" parameterType="int" resultMap="personMapper">
        select * from tb_person where pid=#{pid}
    </select>
    <!--映射Person对象的resultMap(结果映射集)id需要和何resultMap的id一致-->
    <resultMap id="personMapper" type="com.liuYongQi.MyBatis4.pojo.Person">
        <id property="pid" column="pid"></id>
        <result property="pname" column="pname"></result>
        <result property="psex" column="psex"></result>
        <result property="page" column="page"></result>
        <result property="card_id" column="card_id"></result>
        <!--复杂类型的集  嵌入结果映射 – 结果映射自身的集,或者参考一个-->
        <collection property="card" column="card_id" select="selectCardByCid"></collection>
    </resultMap>

    <!--根据卡号id查询卡号对象-->
    <select id="selectCardByCid" resultType="com.liuYongQi.MyBatis4.pojo.Card" parameterType="int">
        select cid cid,ccode ccode from tb_card where cid=#{cid}
    </select>


</mapper>

4.测试

在com.liuYongQi.test.TestCRUD中创建测试类进行测试

package com.liuYongQi.test;

import com.liuYongQi.MyBatis4.dao.ICardDao;
import com.liuYongQi.MyBatis4.dao.IPersonDao;
import com.liuYongQi.MyBatis4.pojo.Card;
import com.liuYongQi.MyBatis4.pojo.Person;
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;


public class TestCRUD {
    //获得SqlSession对象,通过SqlSession操作CRUD
    private SqlSession sqlSession;

    private ICardDao icardDao ;
    private IPersonDao ipersonDao;
    @Before
    public void before(){
        //读取配置文件,获取SQLSessionFactory
        try {
            //通过Resources类加载核心配置文件,得到文件的输入流
            InputStream inputStream = Resources.getResourceAsStream("MyBatisConfig.xml");
            //创建会话工厂,编译配置文件流,sqlSessionFactory
            SqlSessionFactory sqlSessionFactory=new SqlSessionFactoryBuilder().build(inputStream);
            //通过sqlSessionFactory得到sqlSession象
            sqlSession = sqlSessionFactory.openSession();
            //通过sqlSession获得映射实例类的父接口
            icardDao = sqlSession.getMapper(ICardDao.class);
            ipersonDao = sqlSession.getMapper(IPersonDao.class);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    @After
    public void after(){
        sqlSession.commit();
    }
    @Test
    public void testCard(){
        Card card = icardDao.selectCardByCid(1);
        System.out.println(card);
    }



    @Test
   
public void testPerson(){
        Person person = ipersonDao.selectPersonByPid(1);
        System.out.println(person);
    }


}

 

 

二、双向

双向只需要在单向的基础上改动一点点东西就可以了

Card实体类:

package com.liuYongQi.MyBatis4.pojo;

import java.io.Serializable;

/**
 * @ClassName: Card
 * @Description: 身份证tb_card实体类
 * @Author: Administrator
 * @CreateDate: 2018/10/2 20:29
 * @UpdateUser: Administrator
 * @UpdateDate: 2018/10/2 20:29
 * @UpdateRemark: 修改内容
 * @Version: 1.0
 */

public class Card implements Serializable {
    private Integer cid;    //卡号id

    private String ccode;   //卡号

    //一个身份证只属于一个人
    private Person person;
    public Integer getCid() {
        return cid;
    }

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

    public String getCcode() {
        return ccode;
    }

    public void setCcode(String ccode) {
        this.ccode = ccode;
    }

    public Card(Integer cid, String ccode) {
        this.cid = cid;
        this.ccode = ccode;
    }

    public Card(String ccode) {
        this.ccode = ccode;
    }

    public Card() {
    }

    public Person getPerson() {
        return person;
    }

    public void setPerson(Person person) {
        this.person = person;
    }

    @Override
    public String toString() {
        return "Card{" +
                "cid=" + cid +
                ", ccode='" + ccode + '\'' +
                ", person=" + person +
                '}';
    }


}

 CardMapper.xml文件:

<?xml version="1.0" encoding="UTF-8" ?>
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//ibatis.apache.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<!--Card接口注册-->
<mapper namespace="com.liuYongQi.MyBatis4.dao.ICardDao">
 
    <!--根据卡号id查询卡号对象-->
    <select id="selectCardByCid" parameterType="int" resultMap="cardMapper">
        select * from tb_card c,tb_person p where c.cid=p.card_id and c.cid=#{cid}
    </select>

    <!--映射Card对象的resultMap(结果映射集)id需要和何resultMap的id一致-->
    <resultMap id="cardMapper" type="com.liuYongQi.MyBatis4.pojo.Card">
        <id property="cid" column="cid"></id>
        <result property="ccode" column="ccode"></result>
        <association property="person" javaType="com.liuYongQi.MyBatis4.pojo.Person">
            <id property="pid" column="pid"></id>
            <result property="pname" column="pname"></result>
            <result property="psex" column="psex"></result>
            <result property="page" column="page"></result>
            <result property="card_id" column="card_id"></result>
        </association>
    </resultMap>

</mapper>

 

今天的测试就到这里了,谢谢大家的支持!

如果大家想浏览我的下一篇文章,请留言

版权声明:此文章属于原创,不准随意转载:https://blog.csdn.net/LYQ2332826438

猜你喜欢

转载自blog.csdn.net/LYQ2332826438/article/details/83025737