【MyBatis03】resultType、resultMap、模糊查询、动态SQL、数据分页、配置文件连接数据库
目录
MyBatis返回类型
resultType
sql语句执行完后,数据封装的java对象
此对象类型是任意的,需要是该对象所属类的全限定名
<select id="selectUsers" resultType="org.example.domain.User"> select * from user order by `id` </select>
简单参数
可以是一个简单参数如:int,String,Integer
<select id="selectUsers" resultType="int"> select count(*) from user </select>
Map
只能返回一行数据
Map<String, Object> selectUserMapById(int id);
<select id="selectUserMapById" parameterType="java.lang.Integer" resultType="java.util.HashMap"> select id,name from user where id=#{id} </select>
@Test public void testSelectUserMapById(){ SqlSession sqlSession = MybatisUtil.getSqlSession(); UserDao userDao = sqlSession.getMapper(UserDao.class); Map<String, Object> userMap = userDao.selectUserMapById(1); System.out.println(userMap); sqlSession.close(); }
resultMap
概述
结果映射,指定列名和java对象属性的对应关系。
MyBatis默认是找数据库的列名和其同名属性一 一对应,如果不希望这样,则可以使用resultMap
或你的数据库列名和实体类属性名不一样时,也需要使用resultMap
使用
1、先定义 resultMap标签
2、在select、update、insert等标签中使用
<resultMap id="selectUsersMap" type="org.example.domain.User"> <!-- 主键列,使用id标签 column:列名 property:java实体类的属性名 --> <id column="id" property="id"></id> <!-- 非主键列,使用result--> <!-- 这里将pwd、name调换了位置 --> <result column="name" property="pwd"></result> <result column="pwd" property="name"></result> </resultMap> <select id="selectUserById" resultMap="selectUsersMap"> select * from user where id=#{id} </select>
3、再调用接口方法操作数据库
@Test public void testSelectUserById(){ //使用动态代理的方式操作数据库 SqlSession sqlSession = MybatisUtil.getSqlSession(); UserDao userDao = sqlSession.getMapper(UserDao.class); User user = userDao.selectUserById(1); System.out.println(user); }
4、最后输出接口为
User{id=1, name='123', pwd='zs'}可以看到,name、pwd调换了位置
5、除此之外
还可以用于,列名和实体类的所有属性名不同的情况,这个时候就不能用resultType了,需要使用resultMap。
除非,还可以在sql语句中使用 列别名
AS,来改列名和属性名对应,也可以。
因此,resultType和resultMap不要一起用
模糊查询
在java语句中传入like的内容
List<User> selectUserLikeFirstName(String firstName);
<select id="selectUserLikeFirstName" resultType="org.example.domain.User"> select * from user where name like #{firstName} </select>
@Test public void testSelectUserLikeFirstName(){ SqlSession sqlSession = MybatisUtil.getSqlSession(); UserDao userDao = sqlSession.getMapper(UserDao.class); List<User> user = userDao.selectUserLikeFirstName("张%"); System.out.println(user); sqlSession.close(); }
执行日志是这样的
==> Preparing: select * from user where name like ? ==> Parameters: 张%(String) <== Columns: id, name, pwd <== Row: 1, 张三, 123 <== Row: 9, 张飞, 123 <== Total: 2 [User{id=1, name='张三', pwd='123'}, User{id=9, name='张飞', pwd='123'}]
在mapper文件中拼接like的内容
<select id="selectUserLikeFirstName" resultType="org.example.domain.User"> select * from user where name like #{firstName} "%" </select>
只需在mapper中如上用空格分隔开,用双引号包裹字符即可
@Test public void testSelectUserLikeFirstName(){ SqlSession sqlSession = MybatisUtil.getSqlSession(); UserDao userDao = sqlSession.getMapper(UserDao.class); List<User> user = userDao.selectUserLikeFirstName("张"); System.out.println(user); sqlSession.close(); }
动态SQL
概述
sql语句的内容是变化的,可以根据条件获取到不同的sql语句:主要是where的变化
动态sql的实现,使用的是Mybatis提供的标签:
<if>,
<where>,
<foreach>
if
<select id="selectUserIf" resultType="org.example.domain.User"> select * from user <!-- 如果满足test=“”中的条件,则会执行 select * from user where name=#{name} sql语句,否则就只有where之前的语句 --> <if test="name != null and name != '' "> where name=#{name} </if> </select>
但是这种情况,如果where在
<if>外面,而传入的参数又不满足条件,则会出现语法错误的情况,此时可以在where后面加上
1=1或者
id > 0然后
<if>中用
and连接,则可保证语法正确。
当然,Mybatis肯定想到了这种问题,也就是
<where>
where
用来包含多个
<if>标签,当多个
<if>有一个成立的,
<where>会自动增加一个where关键字,并去掉多余的and、or等关键字。
<select id="selectUserWhere" resultType="org.example.domain.User"> select * from user <where> <if test="name != null and name != ''"> name=#{name} </if> </where> </select>
@Test public void testSelectUserWhere(){ SqlSession sqlSession = MybatisUtil.getSqlSession(); UserDao userDao = sqlSession.getMapper(UserDao.class); User user = new User();//这里没有给user的属性赋值 List<User> users = userDao.selectUserWhere(user); for (User user1 : users) { System.out.println(user1); } sqlSession.close(); }
以上代码没有给user的属性赋值,而mapper文件中也没有使用where关键字,而使用
<where>标签代替,最终查出的只有
<where>标签之外的sql语句。
==> Preparing: select * from user ==> Parameters: <== Columns: id, name, pwd <== Row: 1, 张三, 123 <== Row: 2, 李四, 123 <== Row: 3, 王五, 123 <== Row: 4, 赵云, 123 <== Row: 5, 赵六, 123 <== Row: 6, 刘备, 123 <== Row: 7, 宋江, 123 <== Row: 8, 孙八, 123 <== Row: 9, 张飞, 123 <== Total: 9 User{id=1, name='张三', pwd='123'} User{id=2, name='李四', pwd='123'} User{id=3, name='王五', pwd='123'} User{id=4, name='赵云', pwd='123'} User{id=5, name='赵六', pwd='123'} User{id=6, name='刘备', pwd='123'} User{id=7, name='宋江', pwd='123'} User{id=8, name='孙八', pwd='123'} User{id=9, name='张飞', pwd='123'}
而如果,<if>
满足条件的情况下:
如,在创建user对象下方,加入
user.setName("张飞");
查出的结果则为
==> Preparing: select * from user WHERE name=? ==> Parameters: 张飞(String) <== Columns: id, name, pwd <== Row: 9, 张飞, 123 <== Total: 1 User{id=9, name='张飞', pwd='123'}
我们再测试一下Mybatis会不会将多余的or、and关键词删除:
<select id="selectUserWhere" resultType="org.example.domain.User"> select * from user <where> <if test="name != null and name != ''"><!-- 名字不为空的时候执行此字段 --> name=#{name} </if> <if test="id > 5"><!-- 查询的id大于时执行此字段 --> or id>#{id} </if> </where> </select>
这里是,查询姓名=刘备 或者 id>6 的用户
==> Parameters: 刘备(String), 6(Integer) <== Columns: id, name, pwd <== Row: 6, 刘备, 123 <== Row: 7, 宋江, 123 <== Row: 8, 孙八, 123 <== Row: 9, 张飞, 123 <== Total: 4 User{id=6, name='刘备', pwd='123'} User{id=7, name='宋江', pwd='123'} User{id=8, name='孙八', pwd='123'} User{id=9, name='张飞', pwd='123'}
这里是没有给姓名赋值:
user.setId(6);可以看到下方的sql中,并没有
or关键词
==> Preparing: select * from user WHERE id>? ==> Parameters: 6(Integer) <== Columns: id, name, pwd <== Row: 7, 宋江, 123 <== Row: 8, 孙八, 123 <== Row: 9, 张飞, 123 <== Total: 3 User{id=7, name='宋江', pwd='123'} User{id=8, name='孙八', pwd='123'} User{id=9, name='张飞', pwd='123'}
for each
循环java中的数组、List集合的。主要用于sql语句中的
in关键词
如:
select * from user where id in (1,2,3)查询 id 为1,2,3的用户
后面括号中的1、2、3就需要在java中使用数组或List集合封装好,然后由
foreach标签循环
<foreach collection="表示接口中的方法参数的类型,数组就是array,List就是list" item="表示循环的每个元素,自定义的,就是java增强for循环中用来表示当前循环的元素的变量" open="表示开始的元素,如上面需要用括号括起来,则开始元素为'(' " close="表示结束的元素" separator="表示中间每个元素的分隔符,如上面的就需要用逗号','分隔 "> </foreach>
循环简单参数
这是第一种用法,循环List中存放 数字、字符串
<select id="selectUserForeachOne" resultType="org.example.domain.User"> select * from user where id in <foreach collection="list" item="id" open="(" separator="," close=")" > #{id} <!-- 与上面的item对应 --> </foreach> </select>
@Test public void testSelectUserForeachOne(){ SqlSession sqlSession = MybatisUtil.getSqlSession(); UserDao userDao = sqlSession.getMapper(UserDao.class); List<Integer> list = new ArrayList<>(); list.add(1); list.add(2); list.add(3); List<User> users = userDao.selectUserForeachOne(list); for (User user : users) { System.out.println(user); } sqlSession.close(); }
从日志来看,这里Mybatis帮我们循环生成了一个带有占位符的字符串
( ? , ? , ? )
而后也用list中的元素填充了:
Parameters: 1(Integer), 2(Integer), 3(Integer)
==> Preparing: select * from user where id in ( ? , ? , ? ) ==> Parameters: 1(Integer), 2(Integer), 3(Integer) <== Columns: id, name, pwd <== Row: 1, 张三, 123 <== Row: 2, 李四, 123 <== Row: 3, 王五, 123 <== Total: 3 User{id=1, name='张三', pwd='123'} User{id=2, name='李四', pwd='123'} User{id=3, name='王五', pwd='123'}
循环实体类属性
一般情况下,我们都是将参数封装进实体类再存放进集合或数组的,而Mybatis也提供了这种用法
<select id="selectUserForeachTwo" resultType="org.example.domain.User"> select * from user where id in <foreach collection="list" item="user" open="(" separator="," close=")" > #{user.id} <!-- 直接用item.属性名即可 --> </foreach> </select>
List<User> selectUserForeachTwo(List<User> users);
@Test public void testSelectUserForeachTwo(){ SqlSession sqlSession = MybatisUtil.getSqlSession(); UserDao userDao = sqlSession.getMapper(UserDao.class); List<User> list = new ArrayList<>(); for (int i = 1; i <= 3; i++) { User user = new User(); user.setId(i); list.add(user); } List<User> users = userDao.selectUserForeachTwo(list); for (User user : users) { System.out.println(user); } sqlSession.close(); }
执行结果为:
==> Preparing: select * from user where id in ( ? , ? , ? ) ==> Parameters: 1(Integer), 2(Integer), 3(Integer) <== Columns: id, name, pwd <== Row: 1, 张三, 123 <== Row: 2, 李四, 123 <== Row: 3, 王五, 123 <== Total: 3 User{id=1, name='张三', pwd='123'} User{id=2, name='李四', pwd='123'} User{id=3, name='王五', pwd='123'}
sql代码片段
<sql id="userSQL"> 在这里定义sql语句 </sql> <select id="select"> 使用include标签进行复用 <include refid="userSQL"></include> </select>
总结
综上所述:其实,动态sql的本质就是Mybatis帮你拼sql语句的字符串,因此sqlmapper的语句是很灵活的,( )可以自己在foreach外自定义也没问题。
使用数据库配置文件
driver=com.mysql.jdbc.Driver url=jdbc:mysql://localhost:3306/mybatis?useUnicode=true&characterEncoding=utf-8&useSSL=false username=root password=root
<properties resource="db.properties"></properties> <dataSource type="POOLED"> <!-- 配置数据库的各种信息 ${driver}中的字段与properties中的key相对应 --> <property name="driver" value="${driver}"/> <property name="url" value="${url}"/> <property name="username" value="${username}"/> <property name="password" value="${password}"/> </dataSource>
数据分页
1、maven引入依赖
<!-- https://mvnrepository.com/artifact/com.github.pagehelper/pagehelper --> <dependency> <groupId>com.github.pagehelper</groupId> <artifactId>pagehelper</artifactId> <version>5.1.10</version> </dependency>
2、mybatis引入插件
<plugins> <plugin interceptor="com.github.pagehelper.PageInterceptor"></plugin> </plugins>
3、使用
@Test public void testSelectAllUser(){ SqlSession sqlSession = MybatisUtil.getSqlSession(); UserDao userDao = sqlSession.getMapper(UserDao.class); //分页 //pageNum:第几页 //pageSize:每页几行 PageHelper.startPage(2,3);//第二页,三行数据 List<User> users = userDao.selectAllUser(); for (User user : users) { System.out.println(user); } sqlSession.close(); }
最终的输出结果为:
==> Preparing: SELECT count(0) FROM user //这里查询了共有多少行数据,从而判断能分多少页 ==> Parameters: <== Columns: count(0) <== Row: 9 <== Total: 1 ==> Preparing: select * from user LIMIT ?, ? ==> Parameters: 3(Integer), 3(Integer)//这里自动帮我们填充好了limit,从第3行数据开始,分三行数据,也就是每页三行显示第二页 <== Columns: id, name, pwd <== Row: 4, 赵云, 123 <== Row: 5, 赵六, 123 <== Row: 6, 刘备, 123 <== Total: 3 User{id=4, name='赵云', pwd='123'} User{id=5, name='赵六', pwd='123'} User{id=6, name='刘备', pwd='123'}
- 03_MyBatis基本查询,mapper文件的定义,测试代码的编写,resultMap配置返回值,sql片段配置,select标签标签中的内容介绍,配置使用二级缓存,使用别名的数据类型,条件查询ma
- 03_MyBatis基本查询,mapper文件的定义,测试代码的编写,resultMap配置返回值,sql片段配置,select标签标签中的内容介绍,配置使用二级缓存,使用别名的数据类型,条件查询ma
- mybaits(查询与别名、日志框架显示sql语句、对象属性和数据库表字段不匹配resultMap使用、mysql数据查询分页、执行sql和存储过程、动态SQL语句)
- Mybatis+mysql动态分页查询数据案例——Mybatis的配置文件(mybatis-config.xml)
- Mybatis+mysql动态分页查询数据案例——配置映射文件(HouseDaoMapper.xml)
- mybatis配置文件中resultType和resultMap错写后将会封装成属性不一样数据,以及后台报错java.util.HashMap cannot be cast to com.entity
- java springBoot连接数据库进行增删改查、模糊查询、表连接、全选操作、分页操作、数据回显。学习项目实例
- 13、Mybatis基础-maven环境(引入log4j日志、引入数据库配置文件、mybatis占位符与拼接符、动态SQL、Mapper接口开发)
- mybatis配置文件之resultMap和resultType
- mybatis配置文件resultType和resultMap的区别以及mybatis自带的别名
- mybatis-config.xml配置文件及sql分页查询的实现
- mybatis(六) 输入映射 输出映射 resultType:resultMap 动态sql sql片段 if判断 foreach
- ## MyBatis持久层框架,实现数据访问,抽象方法多参数的处理,关于别名,MyBatis中的动态SQL,resultMap
- c#Winform程序调用app.config文件配置数据库连接字符串 SQL Server文章目录 浅谈SQL Server中统计对于查询的影响 有关索引的DMV SQL Server中的执行引擎入门 【译】表变量和临时表的比较 对于表列数据类型选择的一点思考 SQL Server复制入门(一)----复制简介 操作系统中的进程与线程
- mybatis03(配置文件实现一对一动态sql 的增删改查)
- Mybatis 配置resultMap 查询全部sql
- Mybatis (五)输入映射 HashMap输出 传递pojo包装 resultType resultMap 动态sql
- springMVC+mybatis查询数据,返回resultType=”map”时,如果数据为空的字段,则该字段省略不显示的解决方案
- java springBoot连接数据库进行增删改查、模糊查询、表连接、全选操作、分页操作、数据回显。学习项目实例
- java springBoot连接数据库进行增删改查、模糊查询、表连接、全选操作、分页操作、数据回显。学习项目实例