框架:軟件開發中的一套解決方案,不一樣的框架解決不一樣的問題。java
框架的好處:框架封裝了不少的細節,使開發者可使用極簡的方式實現功能,提升開發的效率mysql
三層架構:程序員
一、表現層:用於展現數據sql
二、業務層:用於處理業務需求數據庫
三、持久層:用於和數據庫交互緩存
持久層技術解決方案:tomcat
一、JDBC技術:Connection;PreparedStatement;ResultSet,三個對象服務器
二、Spring的JdbcTemplate:對jdbc的簡單封裝session
三、Apache的DBUtils:對jdbc的簡單封裝mybatis
缺點:操做繁瑣
Mybatis概述:Mybatis是一個優秀的基於java的持久層框架,它內部封裝了jdbc,使開發者只須要關注sql語句自己,而不須要花費精力去處理加載驅動,建立鏈接,建立statement等繁雜的過程。
Mybatis的入門:
一、mybatis的環境搭建:
一、建立maven工程並導入jar包
若是使用maven建立工程,能夠導入下面座標:
<dependency> <groupId>org.mybatis</groupId> <artifactId>mybatis</artifactId> <version>x.x.x</version> </dependency>
二、建立實體類和dao接口
三、建立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"> <!-- mybatis的主配置文件--> <configuration> <!-- 配置環境--> <environments default="mysql"> <!--配置mysql的環境--> <environment id="mysql"> <!--配置事務的類型--> <transactionManager type="JDBC"></transactionManager> <!--配置數據源(鏈接池)--> <dataSource type="POOLED"> <!--配置鏈接數據的4個基本信息--> <property name="driver" value="com.mysql.jdbc.Driver"/> <property name="url" value="jdbc:mysql://localhost:3306/eesy"/> <property name="username" value="root"/> <property name="password" value="111111"/> </dataSource> </environment> </environments> <!--指定映射配置文件的位置,映射配置文件指的是每一個dao獨立的配置文件--> <mappers> <mapper resource="lianbang/wu/IUserDao.xml"/> </mappers> </configuration>
四、建立映射配置文件
<?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 ="lianbang.wu.dao.IUserDao"> <!--配置查詢全部--> <select id="findAll"> select * from user; </select> </mapper>
注意:映射配置文件和對應的接口包結構要相同;
使用步驟:
public class MybatisTest { public static void main(String[] args) throws IOException { //一、讀取配置文件 InputStream in = Resources.getResourceAsStream("sqlMapConfig.xml"); //二、建立sqlSessionFactory工廠 SqlSessionFactoryBuilder builder = new SqlSessionFactoryBuilder(); SqlSessionFactory factory = builder.build(in); //三、使用工廠生產sqlSession對象 SqlSession session = factory.openSession(); //四、使用sqlSession建立dao接口的代理對象 IUserDao userDao = session.getMapper(IUserDao.class); //五、使用代理對象執行方法 List<User> users = userDao.findAll(); for (User user : users){ System.out.println(user); } //六、釋放資源 session.close(); in.close(); } }
Mybatis基於註解的使用:
刪除映射xml文件,直接在dao接口的方法上使用@Select註解,而且指定SQL語句,同時須要在主配置文件中的mapper配置時,使用class屬性指定dao接口的全限定類名。
<mappers> <mapper class="lianbang.wu.dao.IUserDao"/> </mappers>
注意:當實體類和數據庫列名不一致時,須要在映射文件中進行對象映射
<resultMap id="userResultMap" type="User"> <id property="id" column="user_id" /> <result property="username" column="username"/> <result property="password" column="password"/> </resultMap>
Mybatis的CURD:
一、保存數據
映射文件:
<!--保存用戶--> <insert id="saveUser" parameterType="lianbang.wu.domain.User"> insert into user (username,address,sex,birthday) value (#{username},#{address},#{sex},#{birthday}) </insert>
測試代碼:
public void testSave() throws IOException { User user = new User(); user.setUsername("mybatis"); user.setAddress("杭州西湖"); user.setSex("男"); user.setBirthday(new Date()); //一、讀取配置文件 InputStream in = Resources.getResourceAsStream("sqlMapConfig.xml"); //二、建立sqlSessionFactory工廠 SqlSessionFactoryBuilder builder = new SqlSessionFactoryBuilder(); SqlSessionFactory factory = builder.build(in); //三、使用工廠生產sqlSession對象 SqlSession session = factory.openSession(); //四、使用sqlSession建立dao接口的代理對象 IUserDao userDao = session.getMapper(IUserDao.class); //五、使用代理對象執行方法 userDao.saveUser(user); session.commit(); //六、釋放資源 session.close(); in.close(); }
二、修改數據
映射文件:
<!--更新用戶--> <update id="updateUser" parameterType="lianbang.wu.domain.User"> update user set username=#{username},address=#{address},sex=#{sex},birthday=#{birthday} where id=#{id}; </update>
測試代碼:
public void testUpdate() throws IOException { User user = new User(); user.setId(51); user.setUsername("mybatis_update"); user.setAddress("杭州西湖"); user.setSex("男"); user.setBirthday(new Date()); //一、讀取配置文件 InputStream in = Resources.getResourceAsStream("sqlMapConfig.xml"); //二、建立sqlSessionFactory工廠 SqlSessionFactoryBuilder builder = new SqlSessionFactoryBuilder(); SqlSessionFactory factory = builder.build(in); //三、使用工廠生產sqlSession對象 SqlSession session = factory.openSession(); //四、使用sqlSession建立dao接口的代理對象 IUserDao userDao = session.getMapper(IUserDao.class); //五、使用代理對象執行方法 userDao.updateUser(user); session.commit(); //六、釋放資源 session.close(); in.close(); }
三、刪除數據
映射文件:
<!--刪除用戶--> <delete id="deleteUser" parameterType="Integer"> delete from user where id=#{userid}; </delete>
測試代碼:
public void testDelete() throws IOException { Integer uid = 51; //一、讀取配置文件 InputStream in = Resources.getResourceAsStream("sqlMapConfig.xml"); //二、建立sqlSessionFactory工廠 SqlSessionFactoryBuilder builder = new SqlSessionFactoryBuilder(); SqlSessionFactory factory = builder.build(in); //三、使用工廠生產sqlSession對象 SqlSession session = factory.openSession(); //四、使用sqlSession建立dao接口的代理對象 IUserDao userDao = session.getMapper(IUserDao.class); //五、使用代理對象執行方法 userDao.deleteUser(uid); session.commit(); //六、釋放資源 session.close(); in.close(); }
Mybatis中的鏈接池:
Mybatis鏈接池提供了3種方式的配置:
主配置文件SqlMapConfig.xml中的dataSource標籤,type屬性就是表示採用何種鏈接池方式
type屬性的取值:POOLED,採用傳統的javax.sql.DataSource規範中的鏈接池,Mybatis中有針對規範的實現
UNPOOLED,採用傳統的獲取鏈接的方式,雖然也實現了實現了javax.sql.DataSource接口,可是並無使用池的思想
JNDI,採用服務器提供的JNDI技術實現,來獲取DataSource對象,不一樣的服務器所能拿到的DataSource是不同的
若是不是Web或者Maven的war工程,是不能使用的
使用tomcat服務器,採用的鏈接池就是dbcp鏈接池。
mybaits中的事務:
sqlsession的commit和rollback;
session.commit();
session.rollback();
mybaits中的動態sql語句:
if標籤:
<select id="findByCondition" resultType="lianbang.wu.domain.User" parameterType="lianbang.wu.domain.User"> select * from user where 1=1 <if test="userName != null"> and username = #{userName} </if> </select>
where標籤:
<select id="findByCondition" resultType="lianbang.wu.domain.User" parameterType="lianbang.wu.domain.User"> select * from user <where> <if test="userName != null"> and username = #{userName} </if> </where> </select>
foreach標籤:
<select id="findByRange" parameterType="queryvo" resultType="lianbang.wu.domain.User"> select * from user <where> <if test="id!=null and ids.size()>0"> <foreach collection="ids" open="and id in (" close=")" item="id" separator=","> #{id} </foreach> </if> </where> </select>
sql標籤:
<sql id="defauleUser"> select * from user </sql> <select id="findAll" resultType="lianbang.wu.domain.User"> <include refid="defaule"> </include>i </select>
trim標籤
set標籤
chose標籤
Mybatis的多表查詢
一對一的查詢:
方法一:新建一個包含兩個對象全部成員變量的實現類,將查詢結果封裝到裏面
方法二:在其中一個對象中,添加另外一個對象到成員變量中。在映射文件中,對變量進行以下映射
<resultMap id="accountUserMap" type="lianbang.wu.domain.Account"> <id property="id" column="aid"></id> <result property="uid" column="uid"></result> <result property="money" column="money"></result> <association property="user" column="uid" javaType="lianbang.wu.domain.User"> <id property="id" column="id"></id> <result property="username" column="username"></result> <result property="address" column="address"></result> <result property="sex" column="sex"></result> <result property="birthday" column="birthday"></result> </association> </resultMap>
再將查詢結果封裝到對應的對象中。
一對多的查詢:
<resultMap id="accountUserMap" type="lianbang.wu.domain.Account"> <id property="id" column="aid"></id> <result property="uid" column="uid"></result> <result property="money" column="money"></result> <collection property="emplist" ofType="lianbang.wu.domain.emp"> <id column="eid" property="id"></id> <result column="ename" property="name"></result> </collection> </resultMap>
多對多查詢:
等同一對多
延遲加載:
概念:在真正使用數據的時才發起查詢,不用的時候不查詢,按需加載(懶加載),一般在一對多查詢或多對多查詢使用
當即加載:
概念:無論用不用,只要一調用方法,立刻發起查詢,一般在一對對或多對多查詢使用
實現步驟:
一、開啓延遲加載:主配置文件中設置
<settings> <setting name="lazyLoadingEnable" value="true"/> <setting name="aggressiveLazyLoading" value="false"/> </settings>
二、設置延遲加載的ResultMap
<resultMap id="accountUserMaplazyLoad" type="lianbang.wu.domain.Account"> <id property="id" column="aid"></id> <result property="uid" column="uid"></result> <result property="money" column="money"></result> <collection property="emplist" ofType="lianbang.wu.domain.emp"> <id column="eid" property="id"></id> <result column="ename" property="name"></result> </collection> </resultMap>
三、延遲加載的mapper文件:
<select id="accountUserMapLazy" resultMap="accountUserMapLazyLoad"> select * from account </select> <select id ="findUser" parameterType="id" resultType="User"> select * from user where id = #{value} </select>
緩存:
概念:存在於內存中的臨時數據
做用:減小和數據庫的交互次數,提升執行效率
適用於:常常查詢而且不常常改變的,數據的正確與否對最終結果影響不大的
不適用於:常常改變的數據,數據的正確與否對最終的結果影響很大的,例如:商品的庫存,銀行的匯率,股市的牌價
mybatis中的一級緩存:它指的是Mybatis中sqlSession對象的緩存,當咱們執行查詢以後,查詢的結果會同時存入到sqlSession爲咱們提供的一塊區域中,該區域的結構是一個Map,當咱們再次查詢一樣的數據,mybatis會先去sqlSession中查詢是否有,有的話直接拿出來用,當sqlSession對象消失,mybatis的一級緩存也就消失了。
注意:當sqlSession執行修改,添加,刪除,commit,close等方法時,就會清空一級緩存。
mybatis中的二級緩存:它指的是mybatis中的sqlSessionFactory對象的緩存。由同一個SqlSessionFactory對象建立的sqlSession共享其緩存。
二級緩存的使用步驟:
第一步:讓mybatis框架支持二級緩存,在主配置文件中配置
<setting name ="cacheEnabled" value="true"/>
第二步:讓當前的映射文件支持二級緩存
<cache></cache>
第三步:讓當前的操做支持二級緩存
建立多個session對象。注意被實體類要實現序列化接口。
註解開發:
在mybatis中,針對CRUD一共有四種註解:@Select ,@Insert,@Update,@Delete
@Select("select * from user") @Results({ @Result(id = true,column ="id",property = "id"), @Result(column = "name", property = "name")}) List<User> findAll();
多表查詢
一對一
@Select("select * from user") @Results({ @Result(id = true,column ="id",property = "id"), @Result(column = "name", property = "name"), @Result(column = "deptid",property = "dept",one=@One(select = "lianbang.wu.dao.IDeptDao.selectdetpBydi")) }) List<User> findAll();
一對多:
@Select("select * from user") @Results({ @Result(id = true,column ="id",property = "id"), @Result(column = "name", property = "name"), @Result(column = "deptid",property = "dept",many=@Many(select = "lianbang.wu.dao.IDeptDao.selectdetpBydi")) }) List<User> findAll();
二級緩存
@CacheNamespace(blocking = true)
補充:
#{}:表示一個佔位符,向佔位符輸入參數,mybatis自動進行Java類型和jdbc類型轉換。程序員不須要考慮參數的類型,好比:傳入字符串,mybatis最終拼接好的sql就是參數兩邊加單引號,接受pojo數據,可使用OGNL解析出pojo的屬性中
${}:表示sql拼接,將參數的內容不加任何修飾拼接到sql中,也能夠接收pojo數據,使用OGNL解析出pojo的屬性值,缺點不能防止sql注入