ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

Mybatis多对一、一对多处理

2022-03-26 02:33:16  阅读:172  来源: 互联网

标签:name 处理 private id tid student Mybatis 一对 public


前提环境搭建

1.在数据库中创建表

CREATE TABLE `teacher` (
`id` INT(10) NOT NULL,
`name` VARCHAR(30) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=INNODB DEFAULT CHARSET=utf8

INSERT INTO teacher(`id`, `name`) VALUES (1, '秦老师');

CREATE TABLE `student` (
`id` INT(10) NOT NULL,
`name` VARCHAR(30) DEFAULT NULL,
`tid` INT(10) DEFAULT NULL,
PRIMARY KEY (`id`),
KEY `fktid` (`tid`),
CONSTRAINT `fktid` FOREIGN KEY (`tid`) REFERENCES `teacher` (`id`)
) ENGINE=INNODB DEFAULT CHARSET=utf8

INSERT INTO `student` (`id`, `name`, `tid`) VALUES ('1', '小明', '1');
INSERT INTO `student` (`id`, `name`, `tid`) VALUES ('2', '小红', '1');
INSERT INTO `student` (`id`, `name`, `tid`) VALUES ('3', '小张', '1');
INSERT INTO `student` (`id`, `name`, `tid`) VALUES ('4', '小李', '1');
INSERT INTO `student` (`id`, `name`, `tid`) VALUES ('5', '小王', '1');

此时我们的数据就是多个学生对应一个老师,一个老师对应多个学生

然后我们需要先创建一个Maven项目,可参考我之前编写的Maven项目的创建

2.导入相关依赖包

<!-- Mybatis核心 -->
<dependency>
  <groupId>org.mybatis</groupId>
  <artifactId>mybatis</artifactId>
  <version>3.5.7</version>
</dependency>
<!-- junit测试 -->
<dependency>
  <groupId>junit</groupId>
  <artifactId>junit</artifactId>
  <version>4.12</version>
  <scope>test</scope>
</dependency>
<!-- MySQL驱动 -->
<dependency>
  <groupId>mysql</groupId>
  <artifactId>mysql-connector-java</artifactId>
  <version>5.1.3</version>
</dependency>
<!-- lombok插件 -->
<dependency>
  <groupId>org.projectlombok</groupId>
  <artifactId>lombok</artifactId>
  <version>1.18.10</version>
</dependency>

3.创建MyBatis的核心配置文件

先配置一个数据库配置文件db.properties,配置文件存放的位置是src/main/resources目录下

driver=com.mysql.jdbc.Driver
url=jdbc:mysql://192.168.111.131:3306/mybatis?characterEncoding=UTF-8
username=root
password=123456

然后创建MyBatis核心配置文件,习惯上命名为mybatis-config.xml,核心配置文件存放的位置是src/main/resources目录下

<?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>
    <!--引入外部配置文件-->
    <properties resource="db.properties"/>

    <settings>
        <!--实体类驼峰命名与数据库_命名映射开启-->
        <setting name="mapUnderscoreToCamelCase" value="true"/>
    </settings>

    <!--设置连接数据库的环境-->
    <environments default="development">
        <environment id="development">
            <transactionManager type="JDBC"/>
            <dataSource type="POOLED">
                <property name="driver" value="${driver}"/>
                <property name="url" value="${url}"/>
                <property name="username" value="${username}"/>
                <property name="password" value="${password}"/>
            </dataSource>
        </environment>
    </environments>
    <!--引入映射文件-->
    <mappers>
      <mapper resource="mappers/StudentMapper.xml"/>
      <mapper resource="mappers/TeacherMapper.xml"/>
    </mappers> 
</configuration>

4.编写Mybatis工具类

public class MybatisUtils {
    private static SqlSessionFactory sqlSessionFactory;

    static {
        try {
            //读取MyBatis的核心配置文件
            InputStream is = Resources.getResourceAsStream("mybatis-config.xml");
            //创建SqlSessionFactoryBuilder对象
            SqlSessionFactoryBuilder sqlSessionFactoryBuilder = new SqlSessionFactoryBuilder();
            //通过核心配置文件所对应的字节输入流创建工厂类SqlSessionFactory,生产SqlSession对象
            sqlSessionFactory = sqlSessionFactoryBuilder.build(is);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    public static SqlSession getSqlSession(){
        //参数true为设置自动提交
        return sqlSessionFactory.openSession(true);
    }
}

多对一

查询多个学生信息及对应老师信息

1.创建实体类

该地方我们使用的是Lombok配置实体类,可以通过Lombok的配置使用对其进行了解

@Data
public class Student {
    private int id;
    private String name;
    private Teacher teacher;
}
@Data
public class Teacher {
    private int id;
    private String name;
}

2.创建Mapper接口

MyBatis中的mapper接口相当于以前的dao。但是区别在于,mapper仅仅是接口,我们不需要提供实现类。

public interface StudentMapper {

    //查询所有学生信息和对应老师信息
    public List<Student> getStudent();
    
}
public interface TeacherMapper {

    //Teacher在此不需要定义方法

}

3.创建MyBatis的映射文件

注:mapper接口的全类名和映射文件中的命名空间(namespace)保持一致。

方式一:按照查询嵌套处理(子查询)

该方式比较麻烦的就是需要写两个sql语句,将表A查询sql的结果赋给表B的查询sql,理解下来就是类似于子查询

StudentMapper.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.chen.mybatis.mapper.StudentMapper">

    <!--这里resultMap自定义名称,和下方的resultMap对应即可-->
    <select id="getStudent" resultMap="StudentTeacher">
        select * from student
    </select>
    <resultMap id="StudentTeacher" type="com.chen.mybatis.pojo.Student">
        <result property="id" column="id" />
        <result property="name" column="name" />
        <!--复杂属性处理,对象用association,集合用collection-->
        <!--这里column填的是student的外键,也是teacher的主键,javaType绑定我们另一个对象teacher类型,select绑定另一个语句,也就是我们下方的语句-->
        <association property="teacher" column="tid" javaType="com.chen.mybatis.pojo.Teacher" select="teacherInfo" />
    </resultMap>
    <!--不难看出,我们这里的tid也就是上方所传递过来的-->
    <select id="teacherInfo" resultType="com.chen.mybatis.pojo.Teacher">
        select * from teacher where id = #{tid}
    </select>
    
</mapper>

方式二:按照结果嵌套处理(联表查询)简单点

该方式虽然不用写多个sql语句,但是需要给查出来的字段都设置别名,个人感觉的话,可能方式二更容易写一点,当然,不用写多个sql的话其实就是联表查询了

StudentMapper.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.chen.mybatis.mapper.StudentMapper">

    <!--该方式需要给查询出来的字段都取别名-->
    <select id="getStudent" resultMap="StudentTeacher">
        select s.id sid,s.name sname,t.name tname
        from student s,teacher t
        where s.tid = t.id
    </select>
    <!--然后再将查出来的字段与我们的别名进行映射-->
    <resultMap id="StudentTeacher" type="com.chen.mybatis.pojo.Student">
        <result property="id" column="sid" />
        <result property="name" column="sname" />
        <!--这里直接指定另一个表的类型,然后再进行别名映射-->
        <association property="teacher" javaType="com.chen.mybatis.pojo.Teacher">
            <result property="name" column="tname" />
        </association>
    </resultMap>
    
</mapper>

4.测试

public class MybatisTest {

    @Test
    public void testMybatis() {
        SqlSession sqlSession = MybatisUtils.getSqlSession();

        StudentMapper studentMapper= sqlSession.getMapper(StudentMapper.class);

        List<Student> studentList = studentMapper.getStudent();
        for(Student student:studentList){
            System.out.println(student);
        }
        sqlSession.close();
    }

}

一对多

查询一个老师及对应的多个学生信息

1.创建实体类

该地方我们使用的是Lombok配置实体类,可以通过Lombok的配置使用对其进行了解

@Data
public class Student {
    private int id;
    private String name;
    private int tid;
}
@Data
public class Teacher {
    private int id;
    private String name;
    private List<Student> students;
}

2.创建Mapper接口

MyBatis中的mapper接口相当于以前的dao。但是区别在于,mapper仅仅是接口,我们不需要提供实现类。

public interface StudentMapper {

    //Student在此不需要定义方法

}
public interface TeacherMapper {

    //获取指定老师的信息及对应的多个学生的信息
    Teacher getTeacher(int id);

}

3.创建MyBatis的映射文件

注:mapper接口的全类名和映射文件中的命名空间(namespace)保持一致。

方式一:按照查询嵌套处理(子查询)

该方式比较麻烦的就是需要写两个sql语句,将表A查询sql的结果赋给表B的查询sql,理解下来就是类似于子查询

TeacherMapper.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.chen.mybatis.mapper.TeacherMapper">

    <select id="getTeacher" parameterType="int" resultMap="TeacherStudent">
        select * from teacher where id = #{id}
    </select>
    <resultMap id="TeacherStudent" type="com.chen.mybatis.pojo.Teacher">
        <!--这里因为映射的是集合所有用collection,ofType代表集合里的类型-->
        <collection property="students" column="id" ofType="com.chen.mybatis.pojo.Student" select="StudentInfo"/>
    </resultMap>
    <select id="StudentInfo" resultType="com.chen.mybatis.pojo.Student">
        select * from student where tid = #{id}
    </select>
    
</mapper>

方式二:按照结果嵌套处理(联表查询)简单点

该方式虽然不用写多个sql语句,但是需要给查出来的字段都设置别名,个人感觉的话,可能方式二更容易写一点,当然,不用写多个sql的话其实就是联表查询了

TeacherMapper.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.chen.mybatis.mapper.TeacherMapper">

    <select id="getTeacher" parameterType="int" resultMap="TeacherStudent">
        select t.id teid,t.name tename,s.id sid,s.name sname
        from teacher t,student s
        where t.id=s.tid and t.id = #{id};
    </select>
    <resultMap id="TeacherStudent" type="com.chen.mybatis.pojo.Teacher">
        <result property="id" column="teid" />
        <result property="name" column="tename" />
        <!--复杂属性处理,对象用association,集合用collection
            注意这里使用的是ofType不是javaType
        -->
        <collection property="students" ofType="com.chen.mybatis.pojo.Student">
            <result property="id" column="sid" />
            <result property="name" column="sname" />
        </collection>
    </resultMap>

</mapper>

4.测试

public class MybatisTest {
@Test public void testMybatis() { SqlSession sqlSession = MybatisUtils.getSqlSession(); TeacherMapper teacherMapper = sqlSession.getMapper(TeacherMapper.class); Teacher teacher = teacherMapper.getTeacher(1); System.out.println(teacher); sqlSession.close(); }
}

小结

关联 - association  多对一

集合 - collection     一对多

javaType               用来指定我们实体类中属性的类型

ofType                  用来指定集合中的类型


该文档来自狂神说Java

b站视频链接https://www.bilibili.com/video/BV1NE411Q7Nx?p=22&spm_id_from=pageDriver

标签:name,处理,private,id,tid,student,Mybatis,一对,public
来源: https://www.cnblogs.com/cjzzz/p/16057501.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有