是软件开发的一套解决方案,不同的框架解决的事不同的问题。好处:框架封装了很多的细节,使开发者使用极简的方式实现功能。
1.1.2 mybatis:
是持久层的框架,用Java编写,封装了jdbc操作的细节,使开发者之关注sql语句。第一步:创建maven工程并导入坐标
第二部:创建实体类和dao;
第三步:创建主配置文件(SqlMapConfig.xml)
第四部:创建映射配置文件(IUserDao.xml)
创建IUserDao.xml文件和IUserDao.java文件时,名称一致是为了好区分,有时候持久层的映射接口也叫IUserMapper其实是一样的;
idea中包的创建和目录不一样;
com,muzi.dao是三级目录 而在包中是一级目录;
在mybatis中映射文件位置必须Dao接口的包结构相同;
在映射配置文件中,mapper标签的namespace属性的取值必须是dao给定的全限定接口类名(全路径);
映射文件的操作配置,id属性的取值必须dao接口的方法名;
万能的map:
SqlSession sqlSession = MybatisUtils.getSqlSession(); //执行语句 UserMapper mapper = sqlSession.getMapper(UserMapper.class); HashMap<String, String> map = new HashMap<String, String>(); map.put("id","17"); map.put("name","木婉清"); map.put("address","终南山下"); int i = mapper.updateUser2(map); if(i>0){ System.out.println("修改成功"); } sqlSession.commit(); sqlSession.close();以及模糊查寻:
select * from mybatis.user where username like "%"#{username}"%";在mybatis中可以同时配置很多环境:
environments关键字设置别名在对应的.xml 文件中当实体类比较少的时候,可以使用第一种——
<typeAlias type="com.muzi.entity.User" alias="User"/>可以diy别名,当实体类比较多的时候可使用第二种
<package name="com.muzi.entity"/>自动扫描实体类下的包名,但是 只能是类名的小写为别名——使用注解式在实体类下——
@Alias("注解名");然后在UserMapper.xml中设置resulttype=”test“;
当实体类属性名和数据库字段名不一样t;
实体类:id name password
数据库 id name pwd
我们可以使用ResuitMap和取别名的用法
可以使用_取别名 select id name pwd as password from user where id=#{id} 2.可以使用 _resultmap(结果集映射)
<resultMap id="结果集名称" type="实体类名"> <result column="" property=""> 其中column是数据库的字段名,property是实体类属性 3. 在resultmap中属性id‘和result不同; <result column="birthay" property="birthday"/> <!--<id column="birthay" property="birthay"/>-->在数据比较多的时候我们可以使用查询语句的limit;
对于limit(x,v)可以提供两个参数X:第一个参数指定第一个返回记录行的偏移量;v:每页显示的个数;
查询语句
使用limit的分页查询
<!--分页查询--> <select id="getSelectUser" resultType="user" parameterType="map"> select * from mybatis.user limit #{startIndex},#{pageSize} </select>分页查询的其他方法:使用RowBounhaids分页;还可以使用插件来进行分页pagehelpermybatis的插件 [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-lvqIaEBB-1599126387717)(C:\Users\暴走小萝莉\AppData\Roaming\Typora\typora-user-images\image-20200613144114087.png)]
分页的作用:减少数据的处理量;
注解实在UserMapper接口上直接实现的;
/*使用注解式开发*/ public interface UserMapper { //1.先将接口写好 @Select("Select * from user") List<User> getUsers(); }注解绑定接口也是可以配合使用于xml文件 但是需要保证同一包下;
注解的本质:反射机制实现
注解的底层核心:动态代理;
1.在使用注解时:关于**@Param()**注解——
基本型的参数和string类型的参数需要加@Param;引用类型不需要加@Param;如若只有一个基本类型的话,规范可加;在sql中引用的就是@Param()中设定的属性值;Lombok是一个可以使用注解省略get、tostring等方法的插件,可以直接导入依赖;
xml
org.projectlombok lombok 1.18.8 provided2.在idea中下在Lombok安装即可;
在多表联查的时候,多对一的情况咱Mapper映射中有两种情况:
1.1先查询"多表"(多对一的“多”)的信息;
在根据多表的外键查询”一表“(多对一的一)的信息——子查询;
在面对多表连查的时候复杂的属性,需要单独的处理——
**对象——association ***集合——collection所用的属性;
3. 第一种子查询
<mapper namespace="com.muzi.Dao.StuMapper"> <!--先查询所有的学生信息 通过学生的外键Tid去查询老师--> <select id="getStu" resultMap="stutea"> /*select s.sid,s.sname,s.ssex,s.saddress,t.Tname from stu s,Tea t where s.Tid=t.id*/ select * from mybatis.stu </select> <!--结果集映射--> <resultMap id="stutea" type="stu"> <result property="sid" column="sid"/> <result property="sname" column="sname"/> <result property="ssex" column="ssex"/> <result property="saddress" column="saddress"/> <!--对复杂的需要使用association——对象 collection 集合 而老师是一个对象 多对一时--> <association property="tea" column="Tid" javaType="tea" select="getTea"/> </resultMap> <select id="getTea" resultType="tea"> select * from tea where id=#{id} </select> </mapper>按照结果嵌套查询
4.1 多对一的查询按照结果集:
<select id="getStu2" resultMap="StuAandTea"> select s.sid sid,s.sname sname,s.ssex ssex,s.saddress saddress,t.Tname Tname,t.Tsex Tsex from stu s,Tea t where s.Tid=t.id </select> <!--结果集映射--> <resultMap id="StuAandTea" type="stu"> <result property="sid" column="sid"/> <result property="sname" column="sname"/> <result property="ssex" column="ssex"/> <result property="saddress" column="saddress"/> <association property="tea" javaType="tea"> <result property="Tname" column="Tname"/> <result property="Tsex" column="Tsex"/> </association> </resultMap>建议使用按结果集查询
<!--按照结果集--> <select id="getTeaStu" resultMap="TeaStu"> select t.id id,t.Tname tname,t.Tsex tsex,s.sid sid,s.sname sname,s.ssex sex,s.saddress address from tea t ,stu s where t.id=s.Tid and t.id=#{id} </select> <resultMap id="TeaStu" type="tea"> <result property="id" column="id"/> <result property="Tsex" column="tsex"/> <result property="Tname" column="tname"/> <!--对于集合来说可以使用collection 而对于对象来说associate javaType是指定属性类型 ofType是集合中的泛型信息需要遍历--> <collection property="stu" ofType="stu"> <result property="sid" column="sid"/> <result property="ssex" column="sex"/> <result property="sname" column="sname"/> <result property="saddress" column="address"/> </collection> </resultMap>2.使用子查询的方式
<!--按照子查询的方式--> <select id="getTeaStu2" resultMap="TeaStu2"> select id,Tname, Tsex from tea where id=#{id} </select> <resultMap id="TeaStu2" type="tea"> <collection property="stu" javaType="ArrayList" ofType="stu" select="getStu2" column="id" /> </resultMap> <select id="getStu2" resultType="stu"> select * from stu where Tid=#{id} </select> 2.1 注意:在子查询中需要使用的JavaType是“ArrayList”的类型,在一对多中;JavaType是指定属性类型——多对一;而ofType是集合中的泛型信息 约束类用来映射到集合中的pojo类型;
10.1 当出现数据的字段名和实体类的属性不一致时;我们可以采用mybatis中seting的值:mapUnderscoreToCamelCase来开启驼峰规则的自动映射:
mapUnderscoreToCamelCase是否开启驼峰命名自动映射,即从经典数据库列名 A_COLUMN 映射到经典 Java 属性名 aColumn。true | falseFalse10.2 在使用唯一的工具类IDUti获得唯一的id值时,我们需要修改的就是数据库的类型是需要为varchar类型,pojo类型为String
注:在实际的应用中我们不能在where(条件后直接写1=1)这时我们就能引出when来优化代码。where 元素只会在子元素返回任何内容的情况下才插入 “WHERE” 子句。而且,若子句的开头为 “AND” 或 “OR”,where 元素也会将它们去除。
如果 where 元素与你期望的不太一样,你也可以通过自定义 trim 元素来定制 where 元素的功能。
10.3.1 优化后的IF学习可以使用where来优化,可以实现;
<select id="SelectAll" parameterType="map" resultType="blog"> /*可以使用万能的map来进行查询 且parameter(参数类型)为map*/ select * from t_blog <where> <if test="title!=null"> title = #{title} </if> <if test="author!=null"> and author = #{author} </if> </where> </select>当在查询中遇到多个不同条件需要单独查询时,我们可使用choose来实现,在动态sql,通过不同的标签
choose的实际案例
<select id="SelectAllChoose" parameterType="map" resultType="blog"> select * from mybatis.t_blog /*where作为条件必须存在,否则无法进行条件选择*/ <where> <choose> <when test="title !=null" > title=#{title} </when> <when test="author !=null"> and author=#{author} </when> <otherwise> and clickHit=#{clickHit} </otherwise> </choose> </where> </select>**注:**当==中的两个条件都不满足的时候,则执行==下的条件;
2.set的使用案例
Set是基于原sql语句的
<update id="Updateblog" parameterType="map" > update mybatis.t_blog <set> <if test="title !=null"> title=#{title} </if> <if test="author !=null"> author=#{author} </if> </set> where id=#{id} </update>通过标签来实现代码的重复利用
1.1 编写sql语句
<!--代码的重复利用--> <sql id="if_title_author"> <if test="title !=null"> title=#{title} </if> <if test="author!=null"> author=#{author} </if> </sql>1.2 利用标签====实现对sql的语句引用
select * from t_blog <where> <include refid="if_title_author"></include> </where> </select>**注:**做好基于单表来定义查询片段;
在sql标签中不要存在where标签;
10.6.1 在我们使用动态sql查询时,有时需要做的是遍历(针对不同的条件查询),
这时我们的foreach就应用而生它可拼接多个字段;
<select id="SelectAllForeach" parameterType="map" resultType="blog"> select * from t_blog <where> <foreach collection="authors" item="author" open="(" separator="or" close=")"> author=#{author} </foreach> </where> </select>注:open为sql条件语句开始的符号,而separator为条件语句中的分割符,最后close为条件的关闭符;
在.java接口中需要注意的是,collection的名字和测试类中接收的名字要一致;
10.6.2 测试类的数据传参
SqlSession sqlSession = MybatisUtils.getSqlSession(); BlogMapper mapper = sqlSession.getMapper(BlogMapper.class); HashMap map = new HashMap(); ArrayList<String> authors = new ArrayList<String>(); authors.add("木子"); map.put("authors",authors); List<Blog> blogList = mapper.SelectAllForeach(map); for (Blog blog : blogList) { System.out.println(blog); } sqlSession.close(); } 注:在书写时需要注意,在测试类中的参数传值时,我们要从新new两个相对应的数组,map/ArrayList;