mybatis与原生jdbc的对比

引言

在当今的软件开发中,数据库与应用程序之间的交互至关重要。Java作为一种广泛使用的编程语言,提供了多种方式来与数据库建立联系。其中,JDBC(Java Database Connectivity)和MyBatis是两种常用的技术。为了更好地了解Java与数据库之间建立联系的过程,本文将对JDBC与MyBatis进行对比分析。

JDBC介绍

JDBC(Java Database Connectivity)是一种用于执行SQL语句的Java API,可以为多种关系数据库提供统一访问。它由一组用Java语言编写的类和接口组成,是Java访问数据库的标准规范。

jdbc的主要类和接口:

  • ConnectionConnection接口代表与特定数据库的连接,可以执行SQL语句并返回结果。通常,首先需要创建一个Connection对象来建立与数据库的连接。
  • StatementStatement接口用于执行静态SQL语句并返回结果。它可以通过Connection对象创建,并用于执行查询和更新操作。
  • PreparedStatementPreparedStatement接口扩展了Statement接口,并允许执行参数化SQL语句。它提供了设置参数的方法,可以用于执行带有参数的查询和更新。
  • CallableStatementCallableStatement接口扩展了PreparedStatement接口,并允许执行存储过程。它提供了设置输入参数和获取输出参数的方法。
  • ResultSetResultSet接口表示查询操作返回的结果集。通过ResultSet对象,可以检索查询结果中的数据,包括获取列值、列名等。
  • DriverManagerDriverManager类是JDBC API中的核心类,用于管理数据库驱动程序。它提供了用于获取与特定数据库的连接的方法,如getConnection()
  • SQLExceptionSQLException是JDBC API中用于表示异常的类。在执行SQL语句或与数据库交互时,可能会抛出此异常。

jdbc接口方法具体介绍可参考此博客http://t.csdnimg.cn/W3wqG

jdbc的操作数据库的流程

  • 加载数据库驱动:首先需要加载数据库的JDBC驱动,可以使用Class.forName()方法来加载。
Class.forName("com.mysql.jdbc.Driver");
  • 创建数据库连接:使用DriverManager.getConnection()方法来建立与数据库的连接,需要提供数据库的URL、用户名和密码。
Connection connection =
DriverManager.getConnection("jdbc:mysql://localhost:3306/mydb", "username",
"password");
  • 创建Statement对象:使用Connection对象创建Statement对象,用于执行SQL语句。
Statement statement = connection.createStatement();
  • 执行SQL语句:使用Statement对象的executeQuery()或executeUpdate()方法来执行SQL语句。
ResultSet resultSet = statement.executeQuery("SELECT * FROM user");
  • 处理结果集:对于查询语句,executeQuery()方法返回一个ResultSet对象,可以从中获取查询结果。
while (resultSet.next()) {
int id = resultSet.getInt("id");
String name = resultSet.getString("name");
int age = resultSet.getInt("age");
// ...
}
  • 关闭连接和释放资源:使用Connection对象的close()方法关闭连接,并释放相关资源。
connection.close();

jdbc操作数据库具体案例:

用户数据库表:

POJO类

@Data
public class User {
    private Integer userId;
    private String userName;
    private String password;
}

DAO(数据访问对象)

public class UserDAO {
    private static final String URL = "jdbc:mysql://localhost:3306/crud?useSSL=false&useUnicode=true&characterEncoding=UTF8&serverTimezone=UTC";
    private static final String USERNAME = "root";
    private static final String PASSWORD = "root";
    public User getUserById(int userId) {

        User user=null;
        String query = "SELECT * FROM user WHERE user_id = ?";

            try {
                // 加载MySQL数据库驱动
                Class.forName("com.mysql.jdbc.Driver");
            } catch (ClassNotFoundException e) {
                e.printStackTrace(); // 处理异常
            }

        try (
                Connection connection = DriverManager.getConnection(URL, USERNAME, PASSWORD);
             PreparedStatement statement = connection.prepareStatement(query)) {
            // 设置查询参数
            statement.setInt(1, userId);
            try (ResultSet resultSet = statement.executeQuery()) {
                if (resultSet.next()) {
                    user = new User();
                    user.setUserId(resultSet.getInt("user_id")) ;
                    user.setUserName(resultSet.getString("user_name"));
                    user.setPassword(resultSet.getString("password"));
                }
            }
        } catch (SQLException e) {
            // 处理异常
            e.printStackTrace();
        }
        // 返回用户对象
        return user;
    }
}

主函数运行代码:

public class Main {
    public static void main(String[] args) {
        //创建dao对象实例
        UserDAO userDAO=new UserDAO();
        //调用通过id查询对象的方法
        User userById = userDAO.getUserById(1);
        //输出获取结果
        System.out.println(userById);
    }
}

运行结果:

Mybatis介绍

MyBatis是一个优秀的持久层框架,它支持定制化SQL、存储过程以及高级映射。MyBatis消除了几乎所有的JDBC代码和参数的手动设置以及结果集的检索。MyBatis可以使用简单的XML或注解来配置和映射原生信息,将接口和Java的POJOs(Plain Old Java Objects,普通的Java对象)映射成数据库中的记录。

Mybatis执行流程

  • 加载配置文件:MyBatis在启动时,会加载配置文件,包括mybatis-config.xml和映射文件(.xml文件)。
  • 创建SqlSessionFactory:基于MyBatis的配置信息,创建一个SqlSessionFactory实例。SqlSessionFactory是线程安全的,可以被多个线程共享。
  • 创建SqlSession:通过SqlSessionFactory实例,可以创建SqlSession。SqlSession是非线程安全的,应该避免在多个线程中共享SqlSession实例。每个线程都应该拥有自己的SqlSession实例。
  • Mapper调用:在SqlSession中,可以通过Mapper接口调用相应的方法,执行SQL语句。
  • 结果映射:SQL执行的结果会被映射到Java对象中。如果SQL查询返回多行结果,MyBatis会将这些结果映射到一个List中。如果查询返回单行结果,MyBatis会直接映射到对应的Java对象。
  • 关闭SqlSession:当SqlSession实例不再需要时,应该关闭它以释放资源。关闭SqlSession后,不能再使用该实例。

mybatis操作数据库具体案例:

基于上面jdbc使用的用户表以及实体类操作

业务接口以及实现类:

public interface UserService {
    //查询所有用户
    List<User> selectAll();
}
public class UserServiceImpl implements UserService {

    @Override
    public List<User> selectAll() {
        InputStream inputStream=null;
        List<User> userList=null;
        try {
            //读取配置文件
             inputStream= Resources.getResourceAsStream("mybatis/mybatis-config.xml");
             //基于构建者模式创建sqlSessionFactory
            SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
            //基于工厂模式创建sqlSession
            SqlSession sqlSession = sqlSessionFactory.openSession();
            //基于代理模式创建代理对象实例
            UserMapper mapper = sqlSession.getMapper(UserMapper.class);
            userList=mapper.selectAll();
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
        return userList;
    }

数据访问接口:

public interface UserMapper {
    List<User> selectAll();
}

mybatis全局映射文件:

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration
        PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
        "https://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
    <!-- 环境配置 default的值与下面environment的id值相同则使用那个环境-->
    <properties resource="props/db.properties"></properties>
    <environments default="development">
        <environment id="development">
            <transactionManager type="JDBC"></transactionManager>
            <dataSource type="POOLED">
                <property name="driver" value="${jdbc.driverClass}"/>
                <property name="url" value="${jdbc.url}"/>
                <property name="username" value="${jdbc.username}"/>
                <property name="password" value="${jdbc.password}"/>
            </dataSource>
        </environment>

        <environment id="runtime">
            <transactionManager type=""></transactionManager>
            <dataSource type=""></dataSource>
        </environment>
    </environments>

    <mappers>
        <mapper resource="mybatis/mappers/UserMapper.xml"/>
    </mappers>

</configuration>

注意:一定不要忘记在全局配置文件中加载连接数据库文件的配置信息

 <properties resource="props/db.properties"></properties>

否则运行时会报一下错误

### Error querying database.  Cause: java.sql.SQLException: Error setting driver on UnpooledDataSource. Cause: java.lang.ClassNotFoundException: Cannot find class: ${jdbc.driverClass}

数据库文件配置:

jdbc.driverClass=com.mysql.jdbc.Driver
jdbc.url=jdbc:mysql://localhost:3306/crud?useSSL=false&useUnicode=true&characterEncoding=UTF8&serverTimezone=UTC
jdbc.username=root
jdbc.password=root

映射文件代码:

<?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="com.yaorange.mapper.UserMapper">
    <resultMap id="BaseResult" type="com.yaorange.domain.User">
        <id column="user_id" property="userId"></id>
        <result column="user_name" property="userName"></result>
        <result column="password" property="password"></result>
    </resultMap>
    <sql id="BaseField">
        user.user_id, user.user_name, user.password
    </sql>
    <select id="selectAll" resultMap="BaseResult">
        SELECT
           <include refid="BaseField"/>
        FROM
            user
    </select>
</mapper>

运行结果:

ps:(上面的业务层代码依然十分冗余,其实应该把对sqlsession对象的那部分代码抽象成一个工具类,但由于我只是展示mybatis的执行流程所以仅仅演示代码执行过程,并没有做相应的优化.)

mybatis配置介绍:

MyBatis 的配置文件通常是一个 XML 文件,用于配置 MyBatis 的运行时环境。这个文件通常命名为 mybatis-config.xml

配置数据源:

在 mybatis-config.xml 中,需要配置数据源。数据源是用于连接数据库的,一下代码用于动态配置数据源

 <environments default="development">
        <environment id="development">
            <transactionManager type="JDBC"></transactionManager>
            <dataSource type="POOLED">
                <property name="driver" value="${jdbc.driverClass}"/>
                <property name="url" value="${jdbc.url}"/>
                <property name="username" value="${jdbc.username}"/>
                <property name="password" value="${jdbc.password}"/>
            </dataSource>
        </environment>

引入外部属性文件,配置数据库连接信息

<properties resource="props/db.properties"></properties>
配置映射文件:
  <mappers>
        <mapper resource="mybatis/mappers/UserMapper.xml"/>
    </mappers>

原生JDBC与Mybatis的对比:

Mybatis与原生JDBC相比主要有以下改变:

连接管理:

  • 使用JDBC时,每次操作数据库都需要手动建立数据库连接,并在操作完成后关闭连接。这会导致大量的资源浪费和潜在的连接泄漏问题。
  • MyBatis 提供了统一的连接管理,减少了代码中与数据库连接相关的工作量。

SQL 语句编写

  • 使用JDBC时,开发者需要直接编写SQL语句,并在代码中拼接参数。这可能导致 SQL 注入的风险。
  • MyBatis 允许将 SQL 语句与参数分开定义,降低了 SQL 注入的风险。

结果集处理

  • 使用JDBC时,开发者需要手动将结果集转换为 Java 对象。
  • MyBatis 可以自动将结果集映射到 Java 对象,简化了结果集的处理过程。

事务管理

  • 使用JDBC时,事务管理需要手动控制,包括开始事务、提交事务和回滚事务等操作。
  • MyBatis 提供了声明式事务管理,开发者只需关注业务逻辑,而无需关心事务的具体操作。

缓存机制

  • MyBatis 提供了两级缓存机制,包括本地缓存和全局缓存,提高了查询效率。

简化复杂查询

  • 对于复杂的查询和存储过程,使用原生JDBC可能会变得非常复杂和混乱。MyBatis通过映射文件简化了这些复杂查询的编写和管理。

类型转换和结果映射

  • MyBatis 内置了强大的类型转换和结果映射机制,可以方便地处理各种数据类型和结果集的映射问题。

小结

原生JDBC与MyBatis相比,MyBatis在连接管理、SQL语句编写、结果集处理、事务管理、缓存机制、映射文件配置等方面简化了流程。MyBatis提供了统一的连接管理、降低了SQL注入风险、自动映射结果集、声明式事务管理,并提供了丰富的扩展点和集成能力。相比之下,原生JDBC需要手动处理这些繁琐的任务,容易导致资源浪费和安全风险。

  • 28
    点赞
  • 18
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值