Mybatis多表关联查询注解方式动态SQL详细笔记

本文主要是介绍Mybatis多表关联查询注解方式动态SQL详细笔记,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

#{}和${}的区别

#{}

是占位符,是采用预编译方式向sql中传递,可以防止sql注入,如果往sql中传值,使用#{}

一般用于向sql中的列传值

${}

是将内容直接拼到sql语句中,一般不用于向sql中传值,一般用于向sql动态传递列名

一般用于向sql动态传递列名 例如: 排序时 order by 后面的列名是可以改变的

										 例如:   select 后面的列名也可以自由选择

resultMap

多张表关联查询时要使用resultMap

 使用resultMap标签对查询结果进行自定义映射type = "Admin" 最终返回的结果类型
--><resultMap id="adminMap" type="Admin"><id column="adminid" property="id"></id><result column="account" property="account"></result></resultMap><select id="findAdmin" resultMap="adminMap">select id adminid,account from admin</select>

(1). resutlMap 的 id 属性是 resutlMap 的唯一标识,本例中定义为

“adminMap”

(2). resutlMap 的 type 属性是映射的 POJO 类型

(3). id 标签映射主键,result 标签映射非主键

(4). property 设置对象属性名称,column 映射查询结果的列名称

多表关联处理

resultMap元素中的association

collection

collection关联元素处理一对多关联

例如: 专业与学生的一对多关联

	部门与员工的一对多关联

专业一方配置多方集合

public class Major {private  int id;private  String name;private  Student student;private List<Student> students;
}

学生多方,在多方配置一方

public class Student {private  int id;private  int num;private  String name;private  String gender;private  Major major;}

使用resultMap组装查询结果

 <resultMap id="majorMap" type="Major"><id column="id" property="id"></id><result column="name" property="name"></result><collection property="students" javaType="list" ofType="Student"><result column="num" property="num"></result><result column="sname" property="name"></result></collection></resultMap><select id="findMajorById"  parameterType="int" resultMap="majorMap">selectm.id,m.name,s.num,s.name snamefrom major m inner join student s on s.majorid = m.id where m.id = #{id}</select><select id="findMajors" resultMap="majorMap">
selectm.id,m.name,s.num,s.name snamefrom major m inner join student s on s.majorid = m.id</select>

其中,查询单个专业对应的学生需要对应id,查询所有专业下的所有学生则不需要对应专业id

resultMap中的collection标签需要进行子类对象的配置

property元素是最终对象属性的名称,javaType则是对应返回的java对象类型,对于list这种对象则需要使用ofType对其内部的对象进行绑定,本例中list内部存储的是Student对象

association

association多在嵌套查询中使用,将一个多表关联查询拆分为多次查询,先查询主表数据,然后查询关联表数据

<!--    嵌套查询  先查询主表(学生表)--><resultMap id="studentMap1" type="Student"><id column="id" property="id"></id><result column="num" property="num"></result><result column="name" property="name"></result><result column="gender" property="gender"></result>
<!--        封装关联数据--><association property="major" javaType="Major" select="findMajorById" column="majorid"></association></resultMap><select id="findStudentById1" resultMap="studentMap1">select id,num,name,gender,majorid from student where id  =#{id}</select><!--    嵌套查询学生关联的专业--><select id="findMajorById" resultType="Major">select name from major where id  = #{majorid}</select>

(1). select:指定关联查询对象的 Mapper Statement ID 为 findMajorByID

(2). column=“majorid”;关联查询时将majorid列的值传入 findMajorByID,并将 findMajorByID 查询的结果映射到Student的Major属性中

(3).collection 和 association 都需要配置 select 和 column 属性,两者配置方法相同

注解方式

@Insert : 插入 sql , 和 xml insert sql 语法完全一样
@Select : 查询 sql, 和 xml select sql 语法完全一样
@Update : 更新 sql, 和 xml update sql 语法完全一样
@Delete : 删除 sql, 和 xml delete sql 语法完全一样
@Param : 入参
@Results : 设置结果集合
@Result : 结果

使用案例

查询所有信息
@Select("select * from t_emp")
@Results(id = "empMap",value = {
@Result(column = "emp_id",property = "empId",id = true), 
@Result(column = "emp_name",property = "empName"), 
@Result(column = "emp_tel",property = "empTel"), 
@Result(column = "emp_education",property = "empEducation"), 
@Result(column = "emp_birthday",property = "empBirthday")
})
List<Employee> getAll();查询单个信息
@Select("select * from t_emp where emp_id=#{empId}")
@ResultMap(value="empMap")
Employee getById(@Param("empId") Integer empId);插入信息
@Insert("insert into t_emp (emp_id, emp_name, emp_tel, " +
" emp_education, emp_birthday, fk_dept_id" +
" )" values (#{empId}, #{empName}, #{empTel}, " +
" #{empEducation}, #{empBirthday}, #{fkDeptId}" +
" )")
int insert(Employee record);删除信息
@Delete("delete from t_emp where emp_id=#{empId}")
int deleteByPrimaryKey(@Param("empId") Integer empId);

动态SQL

MyBatis 的一个强大的特性之一通常是它的动态 SQL 能力

MyBatis 中用于实现动态 SQL 的元素主要有:

If

where

trim

set

choose (when, otherwise)

foreach

if元素

if标签可以对传入的条件进行判断

 <select id="teachers" resultType="com.geroge.mybatispro.model.Teacher">select * from teacherwhere type = 1<if test="num!=null">and num = #{num}</if><if test="name!=null">or name =#{name}</if><if test="gender!=null">and gender = #{gender}</if></select>

通过对if中的test元素进行编写,判断指定条件是否成立

若成立则执行标签内的语句,但是上述语句若是没有type = 1这一段,则会出现条件均不成立,where后没有语句的情况

此时可以使用标签

例如:

<select id="teachers" resultType="com.geroge.mybatispro.model.Teacher">select * from teacher<where><if test="num!=null">and num = #{num}</if><if test="name!=null">or name =#{name}</if><if test="gender!=null">and gender = #{gender}</if></where></select>

元素会进行判断,如果它包含的标签中有返回值的话,它就插入一个’where’

trim元素

where标签用trim也可以表示,当where后紧随AND或者OR的时候,就去除AND或者OR

<select id="teachers" resultType="com.geroge.mybatispro.model.Teacher">select * from teacher<trim prefix="where" prefixOverrides="and|or"><if test="num!=null">and num = #{num}</if><if test="name!=null">or name =#{name}</if><if test="gender!=null">and gender = #{gender}</if></trim></select>

prefix是前缀,可以写where,prefixOverrides覆盖指定内容

Choose元素

 <select id="teachers" resultType="com.geroge.mybatispro.model.Teacher">select * from teacher<trim prefix="where" prefixOverrides="and|or"><choose><when test="name!=null">name = #{name}</when><otherwise>name = '李老师'</otherwise></choose></trim></select>

choose元素内部可以指定when和otherwise

前者是首次判断,后者是在所有判断均没有结果时执行

类似java中的if else语句

set元素

set元素可以去除语句中最后的逗号

例如:

 <update id="updateTeacher" parameterType="teacher">update teacher<set><if test="num!=null">num = #{num},</if><if test="name!=null">name = #{name},</if><if test="gender!=null">gender = #{gender}</if></set>where  id = #{id}</update>

上述语句中前两个if的语句后都存在逗号,若是只执行其中一个的话最后的查询语句中就会多出一个逗号

set元素可以自动去除语句中多余的逗号

此操作也可以通过trim元素实现

 <update id="updateTeacher" parameterType="teacher">update teacher<trim prefix="set" suffixOverrides="," suffix="where"><if test="num!=null">num = #{num},</if><if test="name!=null">name = #{name},</if><if test="gender!=null">gender = #{gender}</if></trim>where  id = #{id}</update>

foreach元素

此元素主要用于构建in条件时,它可以在SQL语句中进行迭代一个集合

foreach元素的属性主要有item,index,collection,open,separator,close

item属性表示集合中每一个元素进行迭代时的别名,index指定一个名字,用于表示迭代过程中每次迭代到的位置

open表示该语句以什么开始(通畅表示前括号),separator表示每次迭代之间以什么符号作为分隔符

close表示以什么结束(通常为后括号)

在使用foreach的时候最关键的也是最容易出错的就是collection属性,该属性是必须指定的,但在不同的情况下,该属性的值是不一样的

如果传入的是单参数且参数类型是一个List的时候,collection属性值为list

如果传入的是单参数且参数类型是一个array数组的时候,collection的属性值为array

<select id="findTeacher" resultType="com.george.mybatispro.model.Teacher">
select
<foreach item="col" collection="list" separator=",">${col}</foreach>
from-teacher
</select>

这篇关于Mybatis多表关联查询注解方式动态SQL详细笔记的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1110778

相关文章

mybatis的整体架构

mybatis的整体架构分为三层: 1.基础支持层 该层包括:数据源模块、事务管理模块、缓存模块、Binding模块、反射模块、类型转换模块、日志模块、资源加载模块、解析器模块 2.核心处理层 该层包括:配置解析、参数映射、SQL解析、SQL执行、结果集映射、插件 3.接口层 该层包括:SqlSession 基础支持层 该层保护mybatis的基础模块,它们为核心处理层提供了良好的支撑。

SQL中的外键约束

外键约束用于表示两张表中的指标连接关系。外键约束的作用主要有以下三点: 1.确保子表中的某个字段(外键)只能引用父表中的有效记录2.主表中的列被删除时,子表中的关联列也会被删除3.主表中的列更新时,子表中的关联元素也会被更新 子表中的元素指向主表 以下是一个外键约束的实例展示

基于MySQL Binlog的Elasticsearch数据同步实践

一、为什么要做 随着马蜂窝的逐渐发展,我们的业务数据越来越多,单纯使用 MySQL 已经不能满足我们的数据查询需求,例如对于商品、订单等数据的多维度检索。 使用 Elasticsearch 存储业务数据可以很好的解决我们业务中的搜索需求。而数据进行异构存储后,随之而来的就是数据同步的问题。 二、现有方法及问题 对于数据同步,我们目前的解决方案是建立数据中间表。把需要检索的业务数据,统一放到一张M

如何去写一手好SQL

MySQL性能 最大数据量 抛开数据量和并发数,谈性能都是耍流氓。MySQL没有限制单表最大记录数,它取决于操作系统对文件大小的限制。 《阿里巴巴Java开发手册》提出单表行数超过500万行或者单表容量超过2GB,才推荐分库分表。性能由综合因素决定,抛开业务复杂度,影响程度依次是硬件配置、MySQL配置、数据表设计、索引优化。500万这个值仅供参考,并非铁律。 博主曾经操作过超过4亿行数据

第10章 中断和动态时钟显示

第10章 中断和动态时钟显示 从本章开始,按照书籍的划分,第10章开始就进入保护模式(Protected Mode)部分了,感觉从这里开始难度突然就增加了。 书中介绍了为什么有中断(Interrupt)的设计,中断的几种方式:外部硬件中断、内部中断和软中断。通过中断做了一个会走的时钟和屏幕上输入字符的程序。 我自己理解中断的一些作用: 为了更好的利用处理器的性能。协同快速和慢速设备一起工作

性能分析之MySQL索引实战案例

文章目录 一、前言二、准备三、MySQL索引优化四、MySQL 索引知识回顾五、总结 一、前言 在上一讲性能工具之 JProfiler 简单登录案例分析实战中已经发现SQL没有建立索引问题,本文将一起从代码层去分析为什么没有建立索引? 开源ERP项目地址:https://gitee.com/jishenghua/JSH_ERP 二、准备 打开IDEA找到登录请求资源路径位置

MySQL数据库宕机,启动不起来,教你一招搞定!

作者介绍:老苏,10余年DBA工作运维经验,擅长Oracle、MySQL、PG、Mongodb数据库运维(如安装迁移,性能优化、故障应急处理等)公众号:老苏畅谈运维欢迎关注本人公众号,更多精彩与您分享。 MySQL数据库宕机,数据页损坏问题,启动不起来,该如何排查和解决,本文将为你说明具体的排查过程。 查看MySQL error日志 查看 MySQL error日志,排查哪个表(表空间

动态规划---打家劫舍

题目: 你是一个专业的小偷,计划偷窃沿街的房屋。每间房内都藏有一定的现金,影响你偷窃的唯一制约因素就是相邻的房屋装有相互连通的防盗系统,如果两间相邻的房屋在同一晚上被小偷闯入,系统会自动报警。 给定一个代表每个房屋存放金额的非负整数数组,计算你 不触动警报装置的情况下 ,一夜之内能够偷窃到的最高金额。 思路: 动态规划五部曲: 1.确定dp数组及含义 dp数组是一维数组,dp[i]代表

活用c4d官方开发文档查询代码

当你问AI助手比如豆包,如何用python禁止掉xpresso标签时候,它会提示到 这时候要用到两个东西。https://developers.maxon.net/论坛搜索和开发文档 比如这里我就在官方找到正确的id描述 然后我就把参数标签换过来

内核启动时减少log的方式

内核引导选项 内核引导选项大体上可以分为两类:一类与设备无关、另一类与设备有关。与设备有关的引导选项多如牛毛,需要你自己阅读内核中的相应驱动程序源码以获取其能够接受的引导选项。比如,如果你想知道可以向 AHA1542 SCSI 驱动程序传递哪些引导选项,那么就查看 drivers/scsi/aha1542.c 文件,一般在前面 100 行注释里就可以找到所接受的引导选项说明。大多数选项是通过"_