Mybatis基础知识总结(规范步骤)

Mybatis简介

官方文档的介绍:MyBatis 是一款优秀的持久层框架,它支持自定义 SQL、存储过程以及高级映射。MyBatis 免除了几乎所有的 JDBC 代码以及设置参数和获取结果集的工作。MyBatis 可以通过简单的 XML 或注解来配置和映射原始类型、接口和 Java POJO(Plain Old Java Objects,普通老式 Java 对象)为数据库中的记录。

MyBatis 也是一个半自动化的ORM框架(Object Relationship Mapping,对象关系映射)

网站

mybatis.org

Mybatis优点

百度百科

什么是持久化和持久层

持久化(是一个动作)

  1. 数据持久化:将程序的数据在持久状态和瞬时状态转换的过程。
  2. 数据持久化的方式就是存储到数据库中。
  3. 内存:断电后内存中的东西就消失了。

持久层(是一个概念)

  1. Dao层、service层。。。。
  2. 完成持久化的代码块就是持久层

官方文档学习

导入maven依赖

 <dependencies>
        <dependency>
            <groupId>org.mybatis</groupId>
            <artifactId>mybatis</artifactId>
            <version>3.5.1</version>
        </dependency>
        <!-- https://mvnrepository.com/artifact/mysql/mysql-connector-java -->
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <version>5.1.47</version>
        </dependency>
        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>4.12</version>
        </dependency>
    </dependencies>

配置Mybatis核心配置文件

连接数据库,配置mybatis环境。

 <!--设置默认指向数据库-->
    <environments default="dev">
        <!--配置环境,不同环境不同的id名字-->
        <environment id="dev">
            <transactionManager type="JDBC"></transactionManager>
            <!--数据库信息-->
            <dataSource type="POOLED">
                <property name="driver" value="com.mysql.jdbc.Driver"/>
                <property name="url" value="jdbc:mysql://localhost:3306/babytun?useUnicode=true&amp;characterEncoding=UTF-8"/>
                <property name="username" value="root"/>
                <property name="password" value="010619"/>
            </dataSource>
        </environment>
    </environments>

从XML中构建SqlSessionFactory

每个基于 MyBatis 的应用都是以一个 SqlSessionFactory 的实例为核心的。

  • SqlSessionFactory 的实例可以通过 SqlSessionFactoryBuilder 获得。
  • 而 SqlSessionFactoryBuilder 则可以从 XML 配置文件或一个预先配置的 Configuration 实例来构建出 SqlSessionFactory 实例。

在这里插入图片描述


public class MyBatisUtils {
    private static SqlSessionFactory sqlSessionFactory = null;

    static {
        Reader reader = null;
        try {
            reader = Resources.getResourceAsReader("mybatis-config.xml");
            sqlSessionFactory = new SqlSessionFactoryBuilder().build(reader);
        } catch (IOException e) {
            e.printStackTrace();
            throw new ExceptionInInitializerError(e);
        }

    }

    public static SqlSession openSession(){
        return sqlSessionFactory.openSession();
    }
    public static void closeSession(SqlSession session){
        if(session !=null){
            session.close();
        }
    }
}

从SqlSessionFactory 中获取 SqlSession

既然有了 SqlSessionFactory,顾名思义,我们可以从中获得 SqlSession 的实例。SqlSession 提供了在数据库执行 SQL 命令所需的所有方法。你可以通过 SqlSession 实例来直接执行已映射的 SQL 语句。

三个重要的类

SqlSessionFactoryBuilder

  • 这个类可以被实例化、使用和丢弃,一旦创建了 SqlSessionFactory,就不再需要它了。 因此 SqlSessionFactoryBuilder 实例的最佳作用域是方法作用域(也就是局部方法变量)。 你可以重用 SqlSessionFactoryBuilder 来创建多个 SqlSessionFactory 实例,但最好还是不要一直保留着它,以保证所有的 XML 解析资源可以被释放给更重要的事情。

SqlSessionFactory

  • SqlSessionFactory 一旦被创建就应该在应用的运行期间一直存在,没有任何理由丢弃它或重新创建另一个实例。 使用 SqlSessionFactory 的最佳实践是在应用运行期间不要重复创建多次,多次重建 SqlSessionFactory 被视为一种代码“坏习惯”。因此 SqlSessionFactory 的最佳作用域是应用作用域。 有很多方法可以做到,最简单的就是使用单例模式或者静态单例模式。

SqlSession

  • 每个线程都应该有它自己的 SqlSession 实例。SqlSession 的实例不是线程安全的,因此是不能被共享的,所以它的最佳的作用域是请求或方法作用域。 绝对不能将 SqlSession 实例的引用放在一个类的静态域,甚至一个类的实例变量也不行。 也绝不能将 SqlSession 实例的引用放在任何类型的托管作用域中,比如 Servlet 框架中的 HttpSession。 如果你现在正在使用一种 Web 框架,考虑将 SqlSession 放在一个和 HTTP 请求相似的作用域中。 换句话说,每次收到 HTTP 请求,就可以打开一个 SqlSession,返回一个响应后,就关闭它。 这个关闭操作很重要,为了确保每次都能执行关闭操作,你应该把这个关闭操作放到 finally 块中。

创建一个utils工具类

创建sqlSessionFactory 对象

public class MyBatisUtils {
    private static SqlSessionFactory sqlSessionFactory = null;

    static {
        Reader reader = null;
        try {
            reader = Resources.getResourceAsReader("mybatis-config.xml");
            sqlSessionFactory = new SqlSessionFactoryBuilder().build(reader);
        } catch (IOException e) {
            e.printStackTrace();
            throw new ExceptionInInitializerError(e);
        }

    }

通过sqlSessionFactory 创建SqlSession 对象

SqlSession 就是一个操作sql语句的类,他有很多方法可以去操作数据库。
在这里插入图片描述

  public static SqlSession openSession(){
        return sqlSessionFactory.openSession();
    }
    public static void closeSession(SqlSession session){
        if(session !=null){
            session.close();
        }
    }

编写代码

实体类

  1. 实体类的属性要与数据库想匹配
package com.imooc.mybatis.entity;

public class Goods {
    /*生成实体类,与数据库表中的字段匹配*/
    private Integer goodsId;//商品编号
    private String title;//标题
    private String subTitle;//子标题
    private Float originalCost;//原始价格
    private Float currentPrice;//当前价格
    private Float discount;//折扣率
    private Integer isFreeDelivery;//是否包邮 ,1-包邮 0-不包邮
    private Integer categoryId;//分类编号

    public void setGoodsId(Integer goodsId) {
        this.goodsId = goodsId;
    }

    public void setTitle(String title) {
        this.title = title;
    }

    public void setSubTitle(String subTitle) {
        this.subTitle = subTitle;
    }

    public void setOriginalCost(Float originalCost) {
        this.originalCost = originalCost;
    }

    public void setCurrentPrice(Float currentPrice) {
        this.currentPrice = currentPrice;
    }

    public void setDiscount(Float discount) {
        this.discount = discount;
    }

    public void setIsFreeDelivery(Integer isFreeDelivery) {
        this.isFreeDelivery = isFreeDelivery;
    }

    public void setCategoryId(Integer categoryId) {
        this.categoryId = categoryId;
    }

    public Integer getGoodsId() {

        return goodsId;
    }

    public String getTitle() {
        return title;
    }

    public String getSubTitle() {
        return subTitle;
    }

    public Float getOriginalCost() {
        return originalCost;
    }

    public Float getCurrentPrice() {
        return currentPrice;
    }

    public Float getDiscount() {
        return discount;
    }

    public Integer getIsFreeDelivery() {
        return isFreeDelivery;
    }

    public Integer getCategoryId() {
        return categoryId;
    }
}

Dao接口

接口实现类与Mapper.xml

  • goods.xml的作用是让数据库与创建的Goods实体类产生映射关系
  • 书写增删改查的SQL语句。
    在这里插入图片描述
  • namespace(命名空间):区分SQL语句(相当于Java中的包), 相当于是SELECT *FROM t_goods ORDER BY goods_id DESC limit 10语句的别名。
  • select id=“selectAll” :相当于是SQL的名称
<?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="goods">
    <!--书写则删改查语句-->
    <select id="selectAll" resultType="com.imooc.mybatis.entity.Goods">
        SELECT *FROM t_goods ORDER BY goods_id DESC limit 10
    </select>

在这里插入图片描述

  • 如何让Mybatis认识Goods.xml
    <mappers> <mapper resource="mappers/goods.xml"></mapper> </mappers> 在这里插入图片描述

测试类

  • 获取Sqlsession通过创建的utils工具类:session = MyBatisUtils.openSession();
  • 通过sqlsession来使用sql语句:/执行查询语句/
    List list = session.selectList(“goods.selectAll”);//命名空间+运行的id
@Test
    public void testSelectAll() throws Exception {
        SqlSession session = null;
        try {
            session = MyBatisUtils.openSession();
            /*执行查询语句*/
            List<Goods> list = session.selectList("goods.selectAll");//命名空间+运行的id
            for(Goods g : list){
                System.out.println(g.getTitle());
            }
        }catch (Exception e){
            throw e;
        }finally {
            MyBatisUtils.closeSession(session);
        }
    }

CUD实例编写

CRUD标签中部分属性:

  • id 命名空间中的唯一标识
  • parameterType:传入SQL语句的参数类型
  • resultType:SQL语句返回值的类型

select(查询)

  • xml文件配置
    <select id="selectAll" resultType="com.imooc.mybatis.entity.Goods">
        SELECT *FROM t_goods ORDER BY goods_id DESC limit 10
    </select>
  • 测试方法

需要编写的代码只有这一处
在这里插入图片描述

@Test
    public void testSelectAll() throws Exception {
        SqlSession session = null;
        try {
            session = MyBatisUtils.openSession();
            
            /*执行查询语句*/
            List<Goods> list = session.selectList("goods.selectAll");//命名空间+运行的id
            for(Goods g : list){
                System.out.println(g.getTitle());
            }
        }catch (Exception e){
            throw e;
        }finally {
            MyBatisUtils.closeSession(session);
        }
    }
  • sql传参查询
  • parameterType:传入参数的类型
  • 如果传入的parameterType = 1030,则sql语句执行为: select * from t_goods where goods_id = 789
  • #{value}就是进行动态传参的
    <select id="selectById" parameterType="Integer" resultType="com.imooc.mybatis.entity.Goods">
        select * from t_goods where  goods_id = #{value}
    </select>
  • 测试类
   /*执行查询语句*/
            Goods goods = session.selectOne("goods.selectById", 1030);
            System.out.println(goods.getTitle());

insert

  • parameterType:传入的参数是实体类的所有属性,所有要把实体类的包路径导入
  • 插入语句没有返回值
    <insert id="insert" parameterType="com.imooc.mybatis.entity.Goods" >
        INSERT INTO t_goods(title, sub_title, original_cost, current_price, discount, is_free_delivery, category_id)
        VALUES (#{title} , #{subTitle} , #{originalCost}, #{currentPrice}, #{discount}, #{isFreeDelivery}, #{categoryId})

    </insert>
  • 测试类
    先创建goods对象,然后再插入
session = MyBatisUtils.openSession();
            
            
            Goods goods = new Goods();
            goods.setTitle("测试商品");
            goods.setSubTitle("测试子标题");
            goods.setOriginalCost(200f);
            goods.setCurrentPrice(100f);
            goods.setDiscount(0.5f);
            goods.setIsFreeDelivery(1);
            goods.setCategoryId(43);
            //insert()方法返回值代表本次成功插入的记录总数
            int num = session.insert("goods.insert", goods);
  • 提交事务
session.commit();//提交事务数据

update

<update id="updateUser" parameterType="com.zlc.pojo.User">
        UPDATE user SET name = #{name}, pwd = #{name} WHERE id = #{id}
    </update>
  • 测试类
@Test
    public void testUpdateUser() {
        SqlSession sqlSession = MyBatisUtils.getSqlSession();
        UserMapper mapper = sqlSession.getMapper(UserMapper.class);
        mapper.updateUser(new User(5, "zbc", "123123"));

        sqlSession.commit();
        sqlSession.close();
    }

delete

 <delete id="deleteUser" parameterType="int">
        DELETE FROM user WHERE id = #{id};
    </delete>
  • 测试类
 @Test
    public void testDeleteUser() {
        SqlSession sqlSession = MyBatisUtils.getSqlSession();
        UserMapper mapper = sqlSession.getMapper(UserMapper.class);
        mapper.deleteUser(5);

        sqlSession.commit();
        sqlSession.close();
    }

万能Map法

当传入的参数过多的时候,我们不可能把每个属性值都写上,这时候就可以考虑用Map方法

    <select id="selectByTitle" parameterType="java.util.Map" resultType="com.imooc.mybatis.entity.Goods">
        SELECT *FROM t_goods WHERE title = #{title}
    </select>
  • 测试类:
    map中的key对应sql中取的值。
 session = MyBatisUtils.openSession();
            Map param = new HashMap();
            param.put("title","'【德国】爱他美婴幼儿配方奶粉1段800g*2罐 铂金版'");
            List<Goods> list = session.selectList("goods.selectByTitle", param);
            for(Goods g:list){
                System.out.println(g.getTitle()+":"+g.getCurrentPrice());
            }
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

仰望星空的鑫

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值