实现基于接口编程的关键在于DAO是一个代理类, 因此DAO 不应该由用户进行实例化, 应该由框架提供统一的工厂类用来获取DAO. 工厂类中根据DAO类型生成对应的动态代理类返回用户.

// Mapper工厂类(负责生成DAO的动态代理对象)
public class MapperFactory {// SQL会话工厂类private SqlSessionFactory sqlSessionFactory;// 通过SQL会话工厂类实例化public MapperFactory(SqlSessionFactory sqlSessionFactory) {this.sqlSessionFactory = sqlSessionFactory;}// 根据DAO类型获取DAO的动态代理类public <T> T getMapper(Class<T> clazz) {SqlSession session = this.sqlSessionFactory.getSession();return new MapperProxy(session).getMapper(clazz);}}
复制代码

在获取DAO时通过工厂类获取, 此时获取的是DAO的代理类.

UserDAO userDAO = new MapperFactory(sf).getMapper(UserDAO.class);
复制代码

当调用DAO中的接口时, 会自动执行动态代理类中的invoke方法. 在invoke方法中执行数据库操作即可.

// Mapper动态代理类
public class MapperProxy implements InvocationHandler {// SQL会话private SqlSession sqlSession;// 通过SQL会话实例化public MapperProxy(SqlSession sqlSession) {this.sqlSession = sqlSession;}// 获取动态代理类@SuppressWarnings("unchecked")public <T> T getMapper(Class<T> clazz) {return (T) Proxy.newProxyInstance(clazz.getClassLoader(), new Class[] { clazz }, this);}// 执行接口时进入该方法@Overridepublic Object invoke(Object proxy, Method method, Object[] args) throws Throwable {// 接口中方法名称和SQL节点ID相同String statementId = method.getName();// 根据方法名称即可获取对应的SQL节点信息MappedStatement ms = sqlSession.getConfig().getMappedStatement(statementId);if (ms == null) {throw new RuntimeException("无对应的SQL, id:" + statementId);}String type = ms.getStatementType();Object param = (args != null) ? args[0] : null;// 根据SQL类型执行对应的数据库操作方法if ("insert".equals(type)) {return sqlSession.insert(statementId, param);} else if ("update".equals(type)) {return sqlSession.update(statementId, param);} else if ("delete".equals(type)) {return sqlSession.delete(statementId, param);} else if ("select".equals(type)) {return sqlSession.selectList(statementId, param);}return null;}}
复制代码

测试

public static void main(String[] args) {// 创建SQL会话工厂SqlSessionFactory sf = new SqlSessionFactoryBean("*_mapper.xml").build();MapperFactory factory = new MapperFactory(sf);// 通过工厂类获取DAOUserDAO userDAO = factory.getMapper(UserDAO.class);// 调用DAO中方法int count = userDAO.insertUser(new User(1L, "zhangsan", 20, "sssss", "ok"));List<User> userList = userDAO.selectUser();// 输出查询结果System.out.println(count);for (User u : userList) {System.out.println("| " + u.getId() + " | " + u.getUname() + " | ");}}
复制代码

转载于:https://juejin.im/post/5ce40676e51d45599e019d08

Mybatis: 接口编程的实现相关推荐

  1. Mybatis_接口编程

    Mybatis参考使用文档:http://www.mybatis.org/mybatis-3/zh/index.html 1.项目结构 2.新增EmployeeMapper.java接口代码 pack ...

  2. Springboot+Mybatis接口快速上手

    这个作业属于哪个课程 软件工程实践2022年春-F班 这个作业要求在哪里 软件工程实践总结&个人技术博客 这个作业的目标 个人技术博客 其他参考文献 CSDN.博客园 目录 一.技术概述 二. ...

  3. 【转】工厂模式面向接口编程

    为了实现更好的灵活性     应改面向接口编程.因此,应该面向接口提供工场.         比如,Cat,   Dog,   Mouse,都是4条腿会跑的动物.     因此,我们建立一个接口叫做F ...

  4. MyBatis接口的简单实现原理

    MyBatis接口的简单实现原理 用过MyBatis3的人可能会觉得为什么MyBatis的Mapper接口没有实现类,但是可以直接用? 那是因为MyBatis使用Java动态代理实现的接口. 这里仅仅 ...

  5. 黑马java教程是什么_Java教程:揭秘什么是面向接口编程

    先用一个案例来给大家说明一下面向接口编程. 案例:有一个电脑类(Computer),电脑除了有基本的开机关机功能外,还有连接任何外接设备的功能,比如能电脑能连接外置键盘(Keyboard),鼠标(Mo ...

  6. Java面向接口编程,低耦合高内聚的设计哲学

    接口体现的是一种规范和实现分离的设计哲学,充分利用接口可以极大的降低程序中各个模块之间的耦合,提高系统的可维护性以及可扩展性. 因此,很多的软件架构设计理念都倡导"面向接口编程"而 ...

  7. 从针对接口编程到依赖注入

    1.概况说明 2.猫狗大战举例 3.说明为什么要针对接口编程,优点 4.说明为什么要"依赖抽象,不要依赖具体类" 5.说明"依赖倒置"与抽象工厂模式 6.说明& ...

  8. java的知识点13——多态、对象的转型(casting)、final关键字、抽象方法和抽象类、接口的作用、如何定义和使用接口?、接口的多继承、面向接口编程

    多态 多态指的是同一个方法调用,由于对象不同可能会有不同的行为.现实生活中,同一个方法,具体实现会完全不同. 多态的要点: 1. 多态是方法的多态,不是属性的多态(多态与属性无关). 2. 多态的存在 ...

  9. 初识Django —Python API接口编程入门

    初识Django -Python API接口编程入门 一.WEB架构的简单介绍 Django是什么? Django是一个开放源代码的Web应用框架,由Python写成.我们的目标是用Python语言, ...

最新文章

  1. 【建模必备】遗传算法的基本原理与步骤(选择)
  2. Visual Studio 2017正式版发布全纪录
  3. 每日一皮:没有经过测试就运行,自信的表情不言而喻!
  4. 盘点近期大热对比学习模型:MoCo/SimCLR/BYOL/SimSiam
  5. suse系统关闭防火墙
  6. 作为一名SAP从业人员,需要专门学习数学么
  7. 《Linux KVM虚拟化架构实战指南》——导读
  8. java实现调查问卷_jsp70516调查问卷自动生成与分析系统 双数据库 mysql版
  9. android模拟win98中文版,Win98模拟器
  10. 百度地图省市县乡镇街道对应的zoom级别
  11. 计算机里一共录入多少个汉字,计算机操作员之汉字输入方法
  12. 拼多多无货源商家一键上传同行店铺宝贝软件?
  13. 信号与系统——抽样信号的傅里叶变换
  14. 天问:《三体》世界真的存在吗?(太阳系与银河系简介)
  15. ROS2探索(一)Publisher-Subscriber的内部过程
  16. Word 文档乱码-请选择使文档可读的编码 重启电脑-不是解决方法的解决方法(可能已经晚了)
  17. 分布式-全局唯一id
  18. 手把手教学--Python爬取有道词典
  19. 【力扣3题】快乐数有效的字母异位词字符串中的单词数
  20. 计算机睡眠重启后无法识别网络,教您一招解决电脑休眠唤醒后无法使用USB键盘的操作方法...

热门文章

  1. 2.精通前端系列技术之JS模块化开发-深入学习seaJs(四)
  2. iOS学习6_多线程NSThread和GCD
  3. Hibernate缓存-使用Ehcache让实体对象集合对象缓存
  4. XML数据读取方式性能比较(一) (转)
  5. Flex beta2+XFire开发实例
  6. 【hdu 6396】Swordsman
  7. 每日笔记---使用@ConfigurationProperties读取yml配置
  8. ArcGISTiledMapServiceLayer does not support Multi-Layer Caches
  9. 【报告分享】2022电商行业趋势报告.pdf
  10. 【报告分享】2021年网生代线上社交行为洞察报告:95后、00后社交江湖大揭秘.pdf(附下载链接)...