IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 大数据 -> MYBATIS01_概述及优缺点、快速搭建工程、Mybatis的增删改查操作、总结 -> 正文阅读

[大数据]MYBATIS01_概述及优缺点、快速搭建工程、Mybatis的增删改查操作、总结

①. JDBC的缺点(了解)

  • ①. 原始jdbc操作(查询数据)
    在这里插入图片描述
  • ②. 原始jdbc操作(插入数据)

在这里插入图片描述

  • ③. 原始jdbc开发存在的问题如下:
  1. 数据库连接创建、释放频繁造成系统资源浪费从而影响系统性能
  2. sql语句在代码中硬编码,造成代码不易维护,实际应用sql变化的可能较大,sql 变动需要改变java代码
  3. 查询操作时,需要手动将结果集中的数据手动封装到实体中。插入操作时,需要手动将实体的数据设置到sql语句的占位符位置
  • ④. 应对上述问题给出的解决方案:
  1. 使用数据库连接池初始化连接资源
  2. 将sql语句抽取到xml配置文件中
  3. 使用反射、内省等底层技术,自动将实体与表进行属性与字段的自动映射

②. Mybatis概述及优缺点

  1. 与JDBC相比,减少了50%的代码量
  2. SQL代码从程序中彻底分离出来,可以分离
  3. 提供XML标签,支持写动态SQL
  4. 提供映射标签,支持对象与数据库的ORM字段关系映射
  • ③. Mybatis的缺点:
  1. SQL语句编写工作量大,熟练度很高
  2. 数据库移植性比较差,如果切换数据库的话,SQL语句会有很大的差异
  • ④. mybatis的工作原理
  1. 读取MyBatis配置文件mybatis-config.xml。mybatis-config.xml作为MyBatis的全局配置文件,配置了MyBatis的运行环境等信息,其中主要内容是获取数据库连接
  2. 加载映射文件Mapper.xml。Mapper.xml文件即SQL映射文件,该文件中配置了操作数据库的SQL语句,需要在mybatis-config.xml中加载才能执行。mybatis-config.xml可以加载多个配置文件,个配置文件对应数据库中的一张表
  3. 创建会话工厂,通过MyBatis的环境等配置信息构造会话工厂SqlSessionFactory
  4. 创建SqlSession对象。由会话工厂创建SqlSession对象,该对象中包含了执行SQL的所有方法
  5. MyBatis底层定义了一个Executor接口来操作数据库,它会根据SqlSession传递的形参的所有方法
  6. 在Execuotor接口的执行方法中,包含了一个MappedStatement类型的参数,该参数是对映射信息
    的封装,用来存储要映射的SQL语句的id、参数等。Mapper.xml文件中的一个SQL对应一个
    MappedStatement对象,SQL的id是MappedStatement的id
  7. 输入参数映射。在执行方法时,MapperStatement对象会对用户执行SQL语句的输入参数进行定义(可以定义为Map、List、基本数据类型和POJO类型),Executor执行器会通过MappedStatement对象在执行SQL前,将输入的Java对象映射到SQL语句中。这里对输入参数的映射过程就类似于JDBC编程中对PreparedStatement对象设置参数的过程
  8. 输出结果映射。在数据库中执行完SQL语句后,MappedStatement对象会对SQL执行输出的结果进行定义(可以定义为Map和List类型、基本类型、POJO类型),Executor执行器会通MappedSt atement对象在执行SQL语句后,将输出结果映射至Java对象中。这种将输出结果映射到Java对象的过程就类似于JDBC编程中对结果的解析处理过程

在这里插入图片描述

③. 快速搭建Mybatis工程

在这里插入图片描述

		<!--mybatis坐标-->
		<dependency>
		    <groupId>org.mybatis</groupId>
		    <artifactId>mybatis</artifactId>
		    <version>3.4.5</version>
		</dependency>
		<!--mysql对应版本的连接器驱动
		5.7 和 8.0 都用这个驱动
		-->
		<dependency>    
		    <groupId>mysql</groupId>   
		    <artifactId>mysql-connector-java</artifactId>    
		    <version>8.0.26</version>
		    <scope>runtime</scope>
		</dependency>
		<!--单元测试坐标-->
		<dependency>    
		    <groupId>junit</groupId>    
		    <artifactId>junit</artifactId>    
		    <version>4.12</version>    
		    <scope>test</scope>
		</dependency>
		<!--日志坐标-->
		<dependency>    
		    <groupId>log4j</groupId>    
		    <artifactId>log4j</artifactId>    
		    <version>1.2.12</version>
		</dependency>
     <dependency>
        <groupId>org.projectlombok</groupId>
        <artifactId>lombok</artifactId>
        <version>1.16.12</version>
     </dependency>
  • ③. 通过官网写mybatis的配置文件
    在这里插入图片描述
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration
        PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
    <environments default="development">
        <environment id="development">
            <transactionManager type="JDBC"/>
            <dataSource type="POOLED">
                <property name="driver" value="com.mysql.cj.jdbc.Driver"/>
                <property name="url" value="jdbc:mysql://localhost:3306/ssm_mybatis"/>
                <property name="username" value="root"/>
                <property name="password" value="root"/>
            </dataSource>
        </environment>
    </environments>
    <mappers>
        <mapper resource="com/xiaozhi/mapper/UserMapper.xml"/>
    </mappers>
</configuration>

在这里插入图片描述

  • ④. 编写实体类及MyBatis核心文件
@Data
@ToString
public class User {
    private Integer id;
    private String userName;
}
<?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.xiaozhi.dao.UserMapper">
	<select id="findEmpById" resultType="com.xiaozhi.entity.User" parameterType="Integer">
			select * from user where id=#{id};
	</select>
</mapper>
  • ⑤. 编写测试代码
public class EmpTest {
    /*通过id查询*/
    @Test
    public void test1()throws Exception{
        //1.加载配置文件
        InputStream inputStream= Resources.getResourceAsStream("sqlMapConfig.xml");
        //2.获取工厂对象
        SqlSessionFactory sqlSessionFactory=new SqlSessionFactoryBuilder().build(inputStream);
        //3.创建会话对象
        SqlSession sqlSession=sqlSessionFactory.openSession();
        //4.执行操作 namespace+id
        User emp =sqlSession.selectOne("com.xiaozhi.dao.UserMapper.findEmpById",1);
        System.out.println(emp);
        //5.释放资源
        sqlSession.close();
    }
}
  • ⑥. 加入日志文件,可以看到打印的SQL log4j.properties
# log4j.properties
### direct log messages to stdout ###
log4j.appender.stdout=org.apache.log4j.ConsoleAppender
log4j.appender.stdout.Target=System.out
log4j.appender.stdout.layout=org.apache.log4j.PatternLayout
log4j.appender.stdout.layout.ConversionPattern=%d{ABSOLUTE} %5p %c{1}:%L - %m%n

### direct messages to file mylog.log ###
log4j.appender.file=org.apache.log4j.FileAppender
log4j.appender.file.File=D:/mylog.log
log4j.appender.file.layout=org.apache.log4j.PatternLayout
log4j.appender.file.layout.ConversionPattern=%d{ABSOLUTE} %5p %c{1}:%L - %m%n

### set log levels - for more verbose logging change 'info' to 'debug' ###
log4j.rootLogger=debug, stdout

在这里插入图片描述

④. MyBatis的增删改查操作

  • ①. 抽取工具类
public class MybatisUtils {

    /*私有构造方法*/
    private MybatisUtils(){}
    private static SqlSessionFactory sqlSessionFactory;

    static {
        try {
            //1.加载配置文件
            InputStream inputStream= Resources.getResourceAsStream("sqlMapConfig.xml");
            //2.给SqlSessionFactory工厂赋值
            sqlSessionFactory=new SqlSessionFactoryBuilder().build(inputStream);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    //3.获取sqlSession会话对象
    public static SqlSession getSqlSession(){
        return sqlSessionFactory.openSession();
    }
}

  • ②. 查询(查询所有、通过id进行查询、模糊查询)
<?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.xiaozhi.dao.UserMapper">

	<!--查询所有的对象-->
	<select id="findAll" resultType="com.xiaozhi.entity.User">
        select * from user
    </select>
	<!--根据id进行查询-->
	<select id="findUserById" parameterType="Integer" resultType="com.xiaozhi.entity.User">
        select * from user where id=#{id}
    </select>
	<!--模糊查询-->
	<select id="findUserByName" parameterType="String" resultType="com.xiaozhi.entity.User">
        select * from user where username like concat('%',#{value},'%')
    </select>

</mapper>
    /*1.查询所有*/
    @Test
    public void SelectAll()throws Exception{
        //1.加载配置文件
        InputStream inputStream=Resources.getResourceAsStream("sqlMapConfig.xml");
        //2.获取SqlSesiionFactory会话工厂
        SqlSessionFactory sqlSessionFactory=new SqlSessionFactoryBuilder().build(inputStream);
        //3.创建sqlSession会话对象
        SqlSession sqlSession=sqlSessionFactory.openSession();
        //4.执行操作
        List<User> list=sqlSession.selectList("userMapper.findAll");
        System.out.println(list);
        //5.释放资源
        sqlSession.close();
    }

    /*2.通过id查询用户信息*/
    @Test
    public void selectById()throws Exception{
        //1.加载配置文件
        InputStream inputStream=Resources.getResourceAsStream("sqlMapConfig.xml");
        //2.创建SqlSessionFactory工厂对象
        SqlSessionFactory sqlSessionFactory=new SqlSessionFactoryBuilder().build(inputStream);
        //3.创建SqlSession会话对象
        SqlSession sqlSession = sqlSessionFactory.openSession();
        //4.执行sql
        User user=sqlSession.selectOne("userMapper.findUserById",1);
        System.out.println(user);
        //5.释放资源
        sqlSession.close();
    }
    /*3.根据姓名进行模糊查询*/
    @Test
    public void selectByName()throws Exception{
        //1.获取会话对象
        SqlSession sqlSession = MybatisUtils.getSqlSession();
        //2.执行sql
        List<User> list = sqlSession.selectList("userMapper.findUserByName", "x");
        System.out.println(list);
    }   
  • ③. 添加一个用户
    #{id}:从输入user对象中获取id属性值
    <!--插入数据-->
    <insert id="insertUser" parameterType="com.xiaozhi.entity.User">
        insert into user(id,username)values(#{id},#{username})
    </insert>
        /*4.新增一条User记录*/
        @Test
        public void add()throws Exception{
            //1.获取会话对象
            SqlSession sqlSession = MybatisUtils.getSqlSession();
            //2.执行sql
              //2.1 创建User对象
              User user=new User();
              user.setId(2);
              user.setUsername("xiaozhi");
              int row=sqlSession.insert("userMapper.insertUser",user);
              System.out.println(row);
            //3.进行事务的提交
            sqlSession.commit();
            //4.释放资源
            sqlSession.close();
        }
  • ④. 修改一条记录
    <!--修改-->
    <update id="updateUser" parameterType="com.itheima.domain.User">
          update user set username=#{username},password=#{password} where id=#{id}
    </update>
         /*5.修改*/
        @Test
        public void update()throws Exception{
            //1.获取会话对象
            SqlSession sqlSession = MybatisUtils.getSqlSession();
            //2.执行sql
            User user=new User();
            user.setId(2);
            user.setUsername("xiaoxing");  
            int result=sqlSession.update("userMapper.updateUser",user);
            System.out.println(result);
            //3.进行事务的提交
            sqlSession.commit();
            //4.释放资源
            sqlSession.close();
        }
  • ⑤. 通过id进行删除
    <!--删除-->
    <delete id="deleteById" parameterType="java.lang.Integer">
        delete from user where id=#{id}
    </delete>
    /*6.删除*/
    @Test
    public void delete()throws Exception{
        //1.获取会话对象
        SqlSession sqlSession = MybatisUtils.getSqlSession();
        //2.执行sql
        int result=sqlSession.delete("userMapper.deleteById",1);
        System.out.println(result);
        //3.进行事务的提交
        sqlSession.commit();
        //4.释放资源
        sqlSession.close();
    }

⑤. 映射文件总结

  • ①. namespace命名空间:作用就是对sql进行分类化管理,理解sql隔离。通常会设置成包名+sql映射文件名注意:使用namespace代理方式开发,namespace有特殊的作用

  • ②. 通过select执行数据查询<select id="" parameterType="" resultType="">

  1. id:标识映射文件的sql,称为statement的id
    (将sql语句封装mappedStatement对象中,所以将id称为statement的id )
  2. #{}:表示占位符,相当于?
  3. #{id}:其中的id表示接收输入的参数,参数名称是id,如果输入参数是简单类型,#{}中的参数名可以任意,可以value或其他名称
  4. parameterType:指定输入参数类型,这里指定int型
  5. resultType:指定sql输出结果的映射的java类型,resultType表示将单条记录映射成的java对象
<mapper namespace="test">
    <select id="findCustomerById" parameterType="Integer"
	resultType="com.itcast.mybatis.po.User">
	select * from user where id = #{id}
	</select>
</mapper>
  • ③. parameterType 和 resultType
  1. parameterType:在映射文件中通过parameterType指定输入参数的类型
  2. resultType:在映射文件中通过resultType指定输出结果的类型
  • ④. selectOne(statement,parament)和selectList(statement,parament)
  1. 第一个参数statement:映射文件中statement的id,等于=namaspace+statementId
  2. 第二个参数parament:指定和映射文件中所匹配paramtype类型的参数(输入参数)
  3. session.selectOne 结果是与映射文件中所匹配的resultType类型的对象
  • ⑤. selectOne和selectList
  1. selectOne:表示查询出一条记录进行映射。如果使用了selectOne可以实现,那么使用selectLis也可以实现 (List中只有一个对象)
  2. selectList:表示查询出一个列表(多个列表)进行映射,如果使用了,如果使用selectList要查询多天记录,不能使用selectOne
  • ⑥. 模糊查询注意事项
  # 第一种情况是字符串的拼接,会引起sql注入,不推荐使用
	1.select * from user where username like%${value}%2.select * from user where username like concat('%',#{value},'%')
  • ⑦. #{ } 和 ${ }
	#{}:
	  1. #{}表示一个占位符号,#{}接收输入参数,类型可以是简单类型,pojo等
	  2. 如果接受简单类型,#{}里面的可以写成value或其他的
	  3. #{}接受的是pojo。要通过user.user.username的形式获取
	${}:
	  1.表示一个拼接符号,会引起sql注入,所以不建议使用
	  2.${} 接受输入参数,类型可以是简单类型,pojo等  
	  3.${} 接受的是pojo。要通过 user.user.username的形式获取
# 如:需要执行如下的SQL,#{}是预编译处理,是占位符
select * from user where name = #{userName};设userName=TANG
# 看日志我们可以看到解析时将#{userName}替换成了?
select * from user where name = ?;
# 然后再把TANG放进去,外面加上单引号
# 如:需要执行如下的SQL,${}是字符串替换,是拼接符
select * from user where name = #{userName};设userName=yuze
# 看日志可以发现就是直接把值拼接上去了
select * from user where name = yuze;
# 这极有可能发生sql注入,下面举了一个简单的sql注入案例
  大数据 最新文章
实现Kafka至少消费一次
亚马逊云科技:还在苦于ETL?Zero ETL的时代
初探MapReduce
【SpringBoot框架篇】32.基于注解+redis实现
Elasticsearch:如何减少 Elasticsearch 集
Go redis操作
Redis面试题
专题五 Redis高并发场景
基于GBase8s和Calcite的多数据源查询
Redis——底层数据结构原理
上一篇文章      下一篇文章      查看所有文章
加:2022-05-05 11:25:14  更:2022-05-05 11:29:37 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/24 0:57:56-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码