Mybatis学习总结(二)——Mapper代理开发

一、概要

1、原始DAO开发中存在的问题:
(1)DAO实现方法体中存在很多过程性代码。
(2)调用SqlSession的方法(select/insert/update)需要指定Statement的id,存在硬编码,不利于代码维护。

2、Mapper动态代理方法:程序员只需要写dao接口(Mapper),而不需要写dao实现类,由mybatis根据dao接口和映射文件中statement的定义生成接口实现类代理对象。

3、目标:通过一些规则让mybatis根据dao接口和映射文件中statement的定义生成接口实现代理对象。

二、开发规范

1、在XXXmapper.xml中namespace等于mapper接口地址(即mapper.xml文件中的namespace与mapper.java接口的类路径相同)。


2、XXXmapper.java接口中的方法和mapper.xml中的statement的Id一致。
3、mapper.java接口中的方法输入参数和mapper.xml中statement的parameterType指定的类型一致。
4、mapper.java接口中的方法的返回值类型和mapper.xml中statement的resultType指定的类型一致。

注:以上的开发规范主要是对下面的代码进行统一生成

SqlSession sqlSession = sqlSessionFactory.openSession();
User user = sqlSession.selectOne("test.findUserById", id); 
......

 三、UserMapper.java类代码(接口文件)

package com.mybatis.mapper;import java.util.List;import com.mybatis.entity.User;/*** 用户管理mapper接口* @author lxx**/
public interface UserMapper {/** 根据ID查询用户信息 */public User findUserById(int id);/** 根据用户名称模糊查询用户信息 */public List<User> findUserByName(String username);/** 添加用户 */public void insertUser(User user);/** 根据ID删除用户 */public void deleteUser(Integer id);/** 根据ID更新用户 */public void updateUser(User user);}

四、将原来的User.xml拷贝并修改名称为UserMapper.xml,再将UserMapper.xml文件中的namespace改为mapper接口地址

 <!-- namespace命名空间,作用就是对sql进行分类化的管理,理解为sql隔离注意:使用mapper代理开发时,namespace有特殊作用-->
<mapper namespace="com.mybatis.mapper.UserMapper">

注:namespace=mapper接口地址
五、在SqlMapConfig.xml中加载UserMapper.xml

<!-- 加载映射文件 --><mappers><mapper resource="com/mybatis/mapping/User.xml"/><mapper resource="com/mybatis/mapping/UserMapper.xml"/></mappers>

六、JUnit测试UserMapperTest.java

package com.mybatis.test;import java.io.InputStream;
import java.util.Date;
import java.util.List;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.Before;
import org.junit.Test;import com.mybatis.entity.User;
import com.mybatis.mapper.UserMapper;public class UserMapperTest {private SqlSessionFactory sqlSessionFactory;// 此方法是在执行@Test标注的方法之前执行
    @Beforepublic void setUp() throws Exception {String resource = "SqlMapConfig.xml";InputStream inputStream = Resources.getResourceAsStream(resource);// 创建SqlSessionFcatorysqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);}@Testpublic void testFindUserById() {SqlSession sqlSession = sqlSessionFactory.openSession();// 创建Usermapper对象,mybatis自动生成mapper代理对象UserMapper mapper = sqlSession.getMapper(UserMapper.class);User user = mapper.findUserById(1);System.out.println(user);sqlSession.close();}@Testpublic void testFindUserByName() {SqlSession sqlSession = sqlSessionFactory.openSession();// 创建Usermapper对象,mybatis自动生成mapper代理对象UserMapper mapper = sqlSession.getMapper(UserMapper.class);List<User> list = mapper.findUserByName("小");System.out.println(list);sqlSession.close();}@Testpublic void testInsertUser() {SqlSession sqlSession = sqlSessionFactory.openSession();// 创建Usermapper对象,mybatis自动生成mapper代理对象User user = new User();user.setUsername("小东");user.setSex("1");user.setAddress("天津");user.setBirthday(new Date());UserMapper mapper = sqlSession.getMapper(UserMapper.class);mapper.insertUser(user);sqlSession.commit();sqlSession.close();}@Testpublic void testUpdateUser() {SqlSession sqlSession = sqlSessionFactory.openSession();// 创建Usermapper对象,mybatis自动生成mapper代理对象User user = new User();user.setId(2);//必须设置Iduser.setUsername("小刘");user.setSex("1");user.setAddress("北京海淀");user.setBirthday(new Date());UserMapper mapper = sqlSession.getMapper(UserMapper.class);mapper.updateUser(user);sqlSession.commit();sqlSession.close();}@Testpublic void testDeleteUser() {SqlSession sqlSession = sqlSessionFactory.openSession();// 创建Usermapper对象,mybatis自动生成mapper代理对象UserMapper mapper = sqlSession.getMapper(UserMapper.class);mapper.deleteUser(3);sqlSession.commit();sqlSession.close();}}

     原来这个sqlSession可以自动创建一个mapper接口的代理对象!我们只需要把刚刚写好的mapper接口类的字节码对象传给getMapper方法,即可得到一个该接口对应的代理对象,然后我们就可以使用这个代理对象来操作接口中具体的方法了。
  到这里,使用mapper代理的方式开发dao就总结完了,但是有个小细节,由于mapper接口中方法的参数要根据映射文件中的parameterType来指定,而parameterType只有一个,所以mapper接口中所有方法的参数都只有一个!那如果我们要传入两个或多个参数该咋整?这没办法,想要传多个参数还是死了这条心了吧,但是可以解决这个问题,就是对传入的对象进行增强,让传进去的对象包含我们需要的参数即可。这算是个小弊端吧,但是不会影响我们开发。

七、小结

1、用mapper代理开发时只要写2个:

(1)mapper.xml

(2)mapper接口

2、Mapper接口开发需要遵循以下规范:

(1)Mapper.xml文件中的namespace与mapper接口的类路径相同。
(2)Mapper接口方法名和Mapper.xml中定义的每个statement的id相同。 
(3)Mapper接口方法的输入参数类型和mapper.xml中定义的每个sql 的parameterType的类型相同。
(4)Mapper接口方法的输出参数类型和mapper.xml中定义的每个sql的resultType的类型相同。

3、代理对象内部调用selectOne()和selectList():

如果mapper对象返回单个pojo对象(非集合对象)代理对象内部通过selectOne查询数据库,如果mapper方法返回集合对象,代理对象内部通过selectList查询数据库。

4、mapper接口中的方法参数只能有一个是否影响系统开发,mapper接口方法参数只能有一个,系统是否不利于维护?
回答:系统框架中,dao层的代码是被业务层公用的。mapper接口只有一个参数,可以使用包装类型的pojo满足不同的业务方法的需求。

 

转载于:https://www.cnblogs.com/xiaoxi/p/6173534.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/572761.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

mac wordpress php7,Mac 下基于 wordpress 搭建个人博客系统

一、前言这里说的是自己从 wordpress 源码开始搭建一个个人博客系统。当然&#xff0c;很多云端已经直接提供了在线安装的方式&#xff0c;这个就不在本文的讨论范围之内了。二、关于 wordpresswordpress是一款个人博客系统&#xff0c;并逐步演化成一款内容管理系统软件&#…

TypeError: db.addUser is not a function : @(shell):1:1 ——mongoDB创建新用户名密码的方法...

不多说&#xff0c;旧版本使用 db.addUser("root","root") 新版本使用这句会出现这个错误提示 TypeError: db.addUser is not a function : (shell):1:1 新版本用的是 db.createUser({user: "test",pwd: "test",roles: [ { role: &quo…

php多人访问抽奖倒计时一致,Javascript和PHP倒计时器为每个人显示相同的计时器...

我有生成倒计时器所需的脚本,该计时器有一个启动和恢复按钮.我试图做的是在一个控制另一页上的计时器的页面上有启动,停止和重置按钮.因此,如果用户X访问page.html,他们将看到一个0的计时器.Admin X访问admin.html,他们看到计时器为0,但他们也有一个启动,停止和重置按钮.当管理…

将list中的元素按照属性分类成树状的map

技术交流群&#xff1a; 233513714public LinkedHashMap<String, List<TPhoneModel>> queryPhoneList(List<TPhoneModel> list) {LinkedHashMap<String, List<TPhoneModel>> map new LinkedHashMap<>();for (TPhoneModel li : list) {  …

java能传地址吗,详解java的值传递、地址传递、引用传递

一直来觉得对值传递和地址传递了解的很清楚&#xff0c;刚才在开源中国上看到一篇帖子介绍了java中的值传递和地址传递&#xff0c;看完后感受颇深。下边总结下以便更容易理解。按照以前的理解&#xff0c;java中基本数据类型是值传递&#xff0c;对象是地址(引用)传递。给大家…

SpringMVC实现PUT请求上传文件

在JQuery中&#xff0c;我们可以进行REST ful中delete和put的请求&#xff0c;但是在java EE标准中&#xff0c;默认只有在POST请求的时候&#xff0c;servlet 才会通过getparameter()方法取得请求体中的相应的请求参数的数据。而PUT&#xff0c;delete请求的请求体中数据则默认…

jQuery多库共存问题解决方法

一、问题概述: 1、随着jQuery的流行,采用jQuery和$符为命名空间的js库越来越多,当然jQuery的$符也是参照的Prototype库的,所以当多个库同时以$符或者jQuery为命名空间时,那么此时,就会产生冲突。 2、由于jQuery的更新速度过快,所以插件更不上,导致不同版本的jQuery对插件支持的…

java开发技术有什么意义,零基础学Java开发技术有哪些优势和好处?

零基础学Java开发技术有哪些优势和好处&#xff1f;Java开发技术有下列优势&#xff1a;Java编程语言简单、面向对象集中于对象及其接口、分布式处理TCP/IP协议、鲁棒性、安全性、体系结构中立性、可移植性、解释执行、高性能、多线程以及动态性等。零基础学Java开发技术的优势…

[TC SRM 685 div1 lev1] MultiplicationTable2

转载&#xff1a; https://www.linkedin.com/pulse/topcoder-685-multiplicationtable2-yingwu-zhu Note: 生成封闭集合方式。 ProblemFox Ciel is creating a new binary operation.The operation will be denoted $ and it will be defined on the finite set S {0, 1, 2, .…

php树菜单转化为一维菜单,php树型菜单 - iturtle的个人空间 - OSCHINA - 中文开源技术交流社区...

通过处理array,添加level,is_leaf属性实现 树型菜单公共类通过处理array,添加level,is_leaf属性实现 树型菜单/*树形分类添加节点属性*$data, 要处理的节点数组*$pid,父类ID*$prefix, 字段前缀 如chh_pid*$tree array()**/function getTree($data, $pid,$prefix,$tree) {for…

C#-WebForm-★★★JQuery知识——基础知识、选择器、事件★★★

JQuery 与 JS 之间的转换 将JQuery转换为JS —— get(0)  例如&#xff1a;alert( $("#d1").get(0).offsetwidth ); 将JS 转换为JQuery —— $(" ")  例如&#xff1a;$("#d1").click(function(){}); 1、什么是JQuery&#xff1f;   它就是…

Java编号姓名元宝数密码,通过my Eclipse控制台向数据库(SQL2008)中查找、删除、插入信息...

通过my Eclipse控制台向数据库(SQL2008)中查找、删除、插入信息如果编译程序有什么错误还望大家多多指正代码执行所需数据库、架包及java源文件已上传至文件 文件名 SQl_JDBC.zip用my Eclipse控制台操作数据库之前(SQL 2008)之前 应先引入一个架包(sqljdbc4.jar) 在架包导入之后…

matlab 空矩阵耗时,性能 – 更快的方式通过空矩阵乘法初始化数组? (Matlab)

这很奇怪&#xff0c;我看到f更快&#xff0c;而g比你看到的慢。但是他们对我来说都是一样的。也许不同版本的MATLAB&#xff1f;>> g () zeros(1000, 0) * zeros(0, 1000);>> f () zeros(1000)f ()zeros(1000)>> timeit(f)ans 8.5019e-04>> timeit(…

事件对象及其属性

$(function(){$(input).bind(click,function(e){alert(e); //获取对象//event对象的属性alert(e.type);alert(e.target);alert(e.currentTarget);//得到监听元素的DOM&#xff0c;target是点的那个的DOM});$(input).bind(mouseover,function(e){alert(e.relatedTarget);});$(in…

百度网盘php文件怎么打开,如何通过网页版百度网盘下载大文件

最近老张需要在百度网盘下载一个较大的文件&#xff0c;结果他要我必须下载客户端才行&#xff0c;此背景下&#xff0c;在网站找了各种办法&#xff0c;什么模拟手机&#xff0c;F12查看下载链接都不行&#xff0c;最后找到了可行的办法。步骤如下&#xff1a;一&#xff1a;如…

matlab对信号加噪代码,Matlab给信号加噪声

在信号处理中经常需要把噪声叠加到信号上去&#xff0c;在叠加噪声时往往需要满足一定的信噪比&#xff0c;这样产生二个问题&#xff0c;其一噪声是否按指定的信噪比叠加&#xff0c;其二怎么样检验带噪信号中信噪比满足指定的信噪比。在MATLAB中可以用randn产生均值为0方差为…

洛谷 1057——台阶问题(递推与递归二分)

题目描述 有N级的台阶&#xff0c;你一开始在底部&#xff0c;每次可以向上迈最多K级台阶&#xff08;最少1级&#xff09;&#xff0c;问到达第N级台阶有多少种不同方式。 输入输出格式 输入格式&#xff1a; 输入文件的仅包含两个正整数N&#xff0c;K。 输出格式&#xff1…

在matlab中ungetfile后,11条Matlab实用小技巧

2011-02-25 15:361.在用循环画很多图时&#xff0c;为了减少对内存的占用&#xff0c;可以设置图像不显示&#xff0c;直接保存起来。其实也很简单&#xff0c;就是在plot等语句前加上一句&#xff1a;figure(visible,off)。这样画图时就不显示了&#xff01;2.记得很久以前就有…

ngix 创建新的网站

1. 进入ngix 的目录的conf 目录 的 vhosts 2. 复制一份新的v2.edc.com.conf 3. server_name : v2.edc.com root : /ali/...../目录 4. 重启nginx 服务 │ /etc/init.d/nginx start|stop|restart │ │ …

pkcs1转pkcs8 php,openssl RSA密钥格式PKCS1和PKCS8相互转换

openssl 生成pkcs1格式的私钥&#xff0c;密钥长度2048位, (PKCS1)openssl genrsa -out private.pkcs1.pem 2048PKCS1私钥转换为PKCS8openssl pkcs8 -topk8 -inform PEM -in private.pkcs1.pem -outform pem -nocrypt -out private.pkcs8.pem逆过程&#xff1a;PKCS8格式私钥再…