当前位置: 首页 > news >正文

Mybatis Mapper接口和xml绑定的多种方式、内部实现原理和过程

一、绑定方式

1. XML文件方式

在Mybatis中,我们需要创建一个与实体类对应的Mapper接口,然后在该接口上添加方法,这些方法对应着SQL语句。然后,我们需要创建一个XML文件,这个文件中包含了SQL语句和映射关系。

例如,我们有一个User实体类和一个UserMapper接口:

public interface UserMapper {User getUserById(int id);
}

然后,我们可以创建一个名为UserMapper.xml的文件,内容如下:

<mapper namespace="com.example.dao.UserMapper"><select id="getUserById" resultType="com.example.entity.User">SELECT * FROM user WHERE id = #{id}</select>
</mapper>

在这个XML文件中,namespace属性指定了Mapper接口的全限定名,id属性指定了SQL语句的唯一标识符,resultType属性指定了查询结果的类型。

2. 注解方式

Mybatis也支持通过注解的方式来进行映射。首先,需要在Mapper接口上添加@Mapper注解,然后在方法上添加@Select、@Insert、@Update、@Delete等注解来指定SQL语句。

例如,我们可以将上面的UserMapper接口改为注解方式:

import org.apache.ibatis.annotations.*;@Mapper
public interface UserMapper {@Select("SELECT * FROM user WHERE id = #{id}")User getUserById(int id);
}

在这个例子中,@Mapper注解表示这是一个Mapper接口,@Select注解表示这是一个查询语句,#{id}是参数占位符。

3. 需要注意

启动类上添加@MapperScan注解指定扫描路径

@SpringBootApplication
@MapperScan("com.example.mapper") // 指定扫描路径
public class Application {public static void main(String[] args) {SpringApplication.run(Application.class, args);}
}

不用@MapperScan注解,也可以在mybatis-config.xml中配置mapper映射文件的位置和命名空间

<configuration><mappers><mapper resource="com/example/mapper/UserMapper.xml"/> // 指定Mapper映射文件的位置和名称</mappers>
</configuration>

二、实现原理

1. 原理

Mybatis的Mapper接口和xml绑定的原理主要依赖于JDK动态代理技术

而Mybatis中MapperProxy代理类是mybatis实现Mapper接口和xml绑定的核心类之一。它实现了InvocationHandler接口,用于拦截Mapper接口方法的调用,并将方法名和参数传递给SqlSession对象执行相应的SQL语句。

2. MapperProxy代理类的实现过程

  1. 首先,通过JDK动态代理技术生成一个MapperProxy代理类实例。这个代理类实现了Mapper接口,并重写了接口中的方法。
  2. 在重写的方法中,MapperProxy会拦截方法调用,并将方法名和参数传递给SqlSession对象执行相应的SQL语句。
  3. SqlSession对象会根据Mapper接口的namespace值找到对应的mapper.xml文件,并根据id值找到对应的SQL语句。然后,根据返回值类型和参数类型等信息,生成相应的Java代码。这些Java代码会包含对SqlSession的操作,例如查询、更新等操作。最终,SqlSession对象会将这些Java代码编译成字节码,并加载到JVM中运行。
  4. 当SQL语句执行完毕后,SqlSession对象会将结果返回给MapperProxy代理类。然后,MapperProxy代理类会将结果映射为Java对象,并返回给调用者。

3. MapperProxy代理类源码

下面是MapperProxy代理class的核心方法实现:mybatis3.5.9

public class MapperProxy<T> implements InvocationHandler, Serializable {@Overridepublic Object invoke(Object proxy, Method method, Object[] args) throws Throwable {try {if (Object.class.equals(method.getDeclaringClass())) {return method.invoke(this, args);} else {return cachedInvoker(method).invoke(proxy, method, args, sqlSession);}} catch (Throwable t) {throw ExceptionUtil.unwrapThrowable(t);}}private MapperMethodInvoker cachedInvoker(Method method) throws Throwable {try {return MapUtil.computeIfAbsent(methodCache, method, m -> {if (m.isDefault()) {try {if (privateLookupInMethod == null) {return new DefaultMethodInvoker(getMethodHandleJava8(method));} else {return new DefaultMethodInvoker(getMethodHandleJava9(method));}} catch (IllegalAccessException | InstantiationException | InvocationTargetException| NoSuchMethodException e) {throw new RuntimeException(e);}} else {return new PlainMethodInvoker(new MapperMethod(mapperInterface, method, sqlSession.getConfiguration()));}});} catch (RuntimeException re) {Throwable cause = re.getCause();throw cause == null ? re : cause;}}private MethodHandle getMethodHandleJava9(Method method)throws NoSuchMethodException, IllegalAccessException, InvocationTargetException {final Class<?> declaringClass = method.getDeclaringClass();return ((Lookup) privateLookupInMethod.invoke(null, declaringClass, MethodHandles.lookup())).findSpecial(declaringClass, method.getName(), MethodType.methodType(method.getReturnType(), method.getParameterTypes()),declaringClass);}private MethodHandle getMethodHandleJava8(Method method)throws IllegalAccessException, InstantiationException, InvocationTargetException {final Class<?> declaringClass = method.getDeclaringClass();return lookupConstructor.newInstance(declaringClass, ALLOWED_MODES).unreflectSpecial(method, declaringClass);}
}

相关文章:

Mybatis Mapper接口和xml绑定的多种方式、内部实现原理和过程

一、绑定方式 1. XML文件方式 在Mybatis中&#xff0c;我们需要创建一个与实体类对应的Mapper接口&#xff0c;然后在该接口上添加方法&#xff0c;这些方法对应着SQL语句。然后&#xff0c;我们需要创建一个XML文件&#xff0c;这个文件中包含了SQL语句和映射关系。 例如&a…...

Unity性能优化分析篇

性能优化是游戏项目开发中一个重要环节。游戏帧率过低&#xff0c;手机发烫&#xff0c; 包体太大&#xff0c;低端机上跑不起来等, 这些都需要来做优化&#xff0c;不管过去&#xff0c;现在&#xff0c;未来&#xff0c;性能优化都是永恒的话题。 而性能优化首先要掌握的是性…...

一键帮您解决win11最新版画图工具难用问题!

&#x1f984;个人主页:修修修也 ⚙️操作环境:Windows 11 正文 自从win11更新后,新版的画图工具变得非常难用,如: 使用橡皮擦后露出背版马赛克 框住某部分拖动移动时背景露出马赛克剪贴板上图片信息无法直接插入到画图板 目前没有一个好一些的能够在软件内部解决这些问题的方…...

老师的保命大法

数字化高度发达的今天&#xff0c;成绩查询系统已经成为学校教育中不可或缺的一部分。不同于传统的成绩公布方式&#xff0c;成绩查询系统更加高效、便捷&#xff0c;同时也充分保障了每位学生的隐私&#xff0c;今天就来揭秘这个教师保命大法&#xff01; 1、代码查询法 对于…...

Django视图函数和资源

文章目录 1.视图1.1 文件or文件夹1.2 相对和绝对导入urls1.3 视图参数1.4 返回值1.5 响应头1.6 FBV和CBV 2.静态资源2.1 静态文件2.2 媒体文件 1.视图 1.1 文件or文件夹 1.2 相对和绝对导入urls 注意实现&#xff1a;不要再项目根目录做相对导入。 原则&#xff1a; 绝对导入…...

戴建业作品集读书笔记

提示&#xff1a;文章写完后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 文章目录 一、高贵既不屈己从人&#xff0c;也不强人同己君子之交淡如水鄙弃世俗功利&#xff0c;以审美的态度应世观物&#xff0c;不仅美化了平凡的事务&#xff0c;也诗化…...

Linux常用的磁盘使用情况命令汇总

1、查看分区使用百分比 df -h 2、查看指定目录磁盘使用情况 du -hac --max-depth1 /opt 参数&#xff1a;-a 查看所有文件&#xff0c;-c 汇总统计&#xff0c;max-depth1 查看深度为1&#xff0c;2级目录不再统计。 3、常用统计命令汇总...

将按键放到输入框内:

如何将将Button放到输入框内&#xff1f; 效果图&#xff1a; 步骤如下&#xff1a; button 外围用template 包裹一层 <template #suffix v-if"row.WorkerRole TPM"> <el-inputtype"text"v-model"row.JobNumber"placeholder"…...

Java Lambda 表达式常见面试问题与解答

公众号「架构成长指南」&#xff0c;专注于生产实践、云原生、分布式系统、大数据技术分享。 在本文中&#xff0c;我们将讨论一些重要且常见的 Java Lambda 表达式面试问题和解答 1.什么是 Lambda 表达式&#xff1f; lambda表达式只是一个没有任何名称的函数,它甚至可以用作…...

【vue+amap】高德地图绘制多边形区域

参考文档&#xff1a; 高德地图参考手册 高德地图示例代码 1、高德地图控制台创建应用&#xff0c;获取权限ak 高德地图控制台 Ps.本项目里按钮等基础控件使用的是element-ui版本控件 2、项目内全局引入 index.html内引入高德地图代码&#xff1a; <script type"te…...

自定义Graph Component:1.2-其它Tokenizer具体实现

本文主要介绍了Rasa中相关Tokenizer的具体实现&#xff0c;包括默认Tokenizer和第三方Tokenizer。前者包括JiebaTokenizer、MitieTokenizer、SpacyTokenizer和WhitespaceTokenizer&#xff0c;后者包括BertTokenizer和AnotherWhitespaceTokenizer。 一.JiebaTokenizer   Ji…...

docker-compose 部署 MySQL 8

目录 前言MySQL 配置文件(my.cnf)docker-compose.yml安装卸载 前言 Windows/Linux 系统通过 docker-compose 部署 MySQL8.0。 MySQL 配置文件(my.cnf) # 服务端参数配置 [mysqld] usermysql # MySQL启动用户 default-storage-engineINNODB # 创建新表时…...

Java设计模式-结构型模式-适配器模式

适配器模式 适配器模式应用场景案例类适配器模式对象适配器模式接口适配器模式适配器模式在源码中的使用 适配器模式 如图&#xff1a;国外插座标准和国内不同&#xff0c;要使用国内的充电器&#xff0c;就需要转接插头&#xff0c;转接插头就是起到适配器的作用 适配器模式&…...

CCF编程能力等级认证GESP—C++4级—样题1

CCF编程能力等级认证GESP—C4级—样题1 单选题&#xff08;每题 2 分&#xff0c;共 30 分&#xff09;判断题&#xff08;每题 2 分&#xff0c;共 20 分&#xff09;编程题 (每题 25 分&#xff0c;共 50 分)第一题 绝对素数第二题 填幻方 参考答案单选题判断题编程题1编程题…...

Git用pull命令后再直接push有问题

在gitlab新建一个项目&#xff0c;然后拉取到本地&#xff0c;用&#xff1a; git init git pull <远程主机名> 然后就是在本地工作区增加所有文件及文件夹。再添加、提交&#xff0c;都没问题&#xff1a; 但是&#xff0c;git push出问题&#xff1a; 说明本地仓库和…...

C语言不可不敲系列:跳水比赛排名问题

目录 1题干&#xff1a; 2解题思路&#xff1a; 3代码: 4运行结果: 5总结: 1题干&#xff1a; 5位运动员参加了10米台跳水比赛&#xff0c;有人让他们预测比赛结果 A选手说&#xff1a;B第二&#xff0c;我第三&#xff1b; B选手说&#xff1a;我第二&#xff0c;E第四&am…...

Python与ArcGIS系列(二)获取地图文档

目录 0 简述1 获取当前地图文档2 获取磁盘中的地图文档3 获取地图文档的图层0 简述 本篇开始介绍实际代码操作,即利用arcpy(python 包)执行地理数据分析、数据转换、数据管理和地图自动化。通过arcpy调用ArcGIS中任意工具,将其与其他python工具结合使用,形成自己的工作流…...

Ansible自动化部署工具-role模式安装filebeat实际案例分析

语法以及实际案例 平时我们在进行日志收集的时候&#xff0c;往往会在每台机器上安装filebeat&#xff0c;并且由于每台机器运行服务的不同&#xff0c;那么收集日志的配置文件也是不一样的&#xff0c;如何快速高效的部署filebeat以及拥有不同的配置文件就是我们要思考的问题&…...

B2B企业如何打造独立站:从策略到实施的全面指南

随着数字化转型的加速&#xff0c;B2B企业越来越认识到独立站的重要性。然而&#xff0c;如何建设一个优秀的独立站&#xff0c;以及如何将独立站与企业的整体战略相结合&#xff0c;是许多企业面临的挑战。本文将详细探讨B2B企业如何从策略到实施打造一个成功的独立站。 一、…...

JAVA 中集合取交集

日常工作 经常需要取两个数据集的交集。对常用的List 和Set集合做了一个测试 public static void main(String[] args) {List<Integer> list1 Lists.newArrayList();List<Integer> list2 Lists.newArrayList();Set<Integer> set3 Sets.newHashSet();Set&l…...

Unity URP 中 Mipmap 纹理多级渐远技术 解决远处纹理闪烁(摩尔纹)与性能优化的完整指南

什么是 Mipmap&#xff1f;Mipmap&#xff08;多重贴图渐远技术&#xff09;是一种经典的纹理渲染优化技术。它为每张纹理生成一系列预计算的缩小版本&#xff0c;从原始分辨率开始&#xff0c;逐级缩小至 11 像素。工作原理当 3D 场景中的物体远离摄像机时&#xff0c;其在屏幕…...

告别电量焦虑:能源之星X如何让Windows笔记本续航轻松翻倍

告别电量焦虑&#xff1a;能源之星X如何让Windows笔记本续航轻松翻倍 【免费下载链接】EnergyStarX &#x1f50b; Improve your Windows 11 devices battery life. A WinUI 3 GUI for https://github.com/imbushuo/EnergyStar. 项目地址: https://gitcode.com/gh_mirrors/en…...

【实战】CodeBuddy使用技巧:5个Skills让编程效率翻倍的隐藏操作

目录摘要一、CodeBuddy不只是代码补全1.1 三种形态&#xff0c;覆盖全开发场景1.2 核心差异化二、Craft模式&#xff1a;一句话从0到上线2.1 实测案例&#xff1a;20分钟出一个完整MVP2.2 多模型切换策略2.3 Figma设计稿一键转代码三、5个效率翻倍的独有技巧3.1 技巧1&#xff…...

矩阵理论进阶:内积空间与正交变换的深度解析

1. 内积空间&#xff1a;从几何直觉到严格定义 第一次接触内积空间时&#xff0c;很多人会被各种抽象定义搞得晕头转向。其实我们可以从最熟悉的二维平面开始理解——当你计算两个向量的点积时&#xff0c;本质上是在测量它们的"相似程度"。这种几何直觉正是内积空间…...

UE5材质编辑器进阶:手把手教你创建并调用自定义ush函数库(附避坑指南)

UE5材质编辑器进阶&#xff1a;打造高效可复用的自定义ush函数库 在虚幻引擎5的材质创作中&#xff0c;重复编写相同的HLSL代码不仅效率低下&#xff0c;还容易引入错误。本文将带你深入理解如何创建并调用自定义ush函数库&#xff0c;提升材质开发的专业性和可维护性。 1. 为什…...

MDS vs PCA:哪种降维方法更适合你的数据?

MDS与PCA深度对比&#xff1a;从算法原理到实战选型指南 当面对高维数据时&#xff0c;降维技术就像一把打开数据奥秘的钥匙。在众多降维方法中&#xff0c;多维尺度变换(MDS)和主成分分析(PCA)是最常被比较的两种经典技术。它们都能将复杂的高维数据简化为更易理解的二维或三维…...

Mermaid Live Editor:3分钟学会专业图表制作的终极免费工具

Mermaid Live Editor&#xff1a;3分钟学会专业图表制作的终极免费工具 【免费下载链接】mermaid-live-editor Edit, preview and share mermaid charts/diagrams. New implementation of the live editor. 项目地址: https://gitcode.com/GitHub_Trending/me/mermaid-live-e…...

Stable Diffusion v1.5功能体验:Guidance Scale参数实测,教你调出最佳效果

Stable Diffusion v1.5功能体验&#xff1a;Guidance Scale参数实测&#xff0c;教你调出最佳效果 1. 引言&#xff1a;为什么Guidance Scale如此重要&#xff1f; 如果你用过Stable Diffusion生成图片&#xff0c;一定遇到过这样的情况&#xff1a;同样的提示词&#xff0c;…...

视频PPT提取终极指南:3步从视频中智能提取演示文稿

视频PPT提取终极指南&#xff1a;3步从视频中智能提取演示文稿 【免费下载链接】extract-video-ppt extract the ppt in the video 项目地址: https://gitcode.com/gh_mirrors/ex/extract-video-ppt 你是否曾经需要从视频中提取PPT内容&#xff0c;却苦于手动截图效率低…...

为什么90%的词库转换都会失败?输入法词库迁移的终极解决方案:全方位指南

为什么90%的词库转换都会失败&#xff1f;输入法词库迁移的终极解决方案&#xff1a;全方位指南 【免费下载链接】imewlconverter ”深蓝词库转换“ 一款开源免费的输入法词库转换程序 项目地址: https://gitcode.com/gh_mirrors/im/imewlconverter 在数字化时代&#x…...