MyBatis筆記(三)——ResultMap結果集映射,日誌,分頁的多種實現方式
參考: https://www.bilibili.com/video/BV1NE411Q7Nx
視頻原作者CSDN: https://blog.csdn.net/qq_33369905
這篇是自己整理了一下,以便自己複習。
1.ResultMap(結果集映射)
1.1 ResultMap自動映射
以下這一段文字摘自MyBatis
自動映射及原理
https://blog.csdn.net/fageweiketang/article/details/80919716
在 MyBatis 的映射配置文件中,select 標籤查詢配置結果集時使用過 resultType 屬性,當在 resultType 中定義一個 Java 包裝類時,如果 sql 語句查詢的結果中有列名與該 Java 包裝類中的屬性名一致,則該字段就會被映射到該屬性上。這裏用到的就是 MyBatis 的自動映射功能,當 sql 語句查詢出結果時**,如果對應輸出配置的 Java 包裝類中有相同名稱的屬性,且擁有 set 方法,則該結果就會被自動映射**。
在第一篇筆記中User類和數據庫中得user表的字段一一對應,如下表,MyBatis已經用ResultMap幫我們自動映射了實體類與user表(命名規則滿足駝峯命名規則即可)。
User類 | user表 | 說明 |
---|---|---|
int id | id int(20) | 用戶ID |
String name | name varchar(30) | 用戶名 |
String pwd | pwd varchar(30) | 密碼 |
UserMapper接口類
public interface UserMapper {
//查詢所有User
List<User> selectUser();
}
UserMapper.xml(片段)
<select id="selectUser" resultType="com.piao.pojo.User">
select id,name,pwd from user
</select>
將User類當中的pwd屬性名改爲password之後再測試查找user的方法時, 查詢出來發現 password 爲null
//查詢所有用戶結果
User{id=2, name='張三', pasword='null'}
User{id=3, name='李四', password='null'}
User{id=5, name='趙六', password='null'}
因爲MyBatis ResultMap自動映射是找User類中名爲pwd的屬性和對應的set方法,沒找到,所以password 爲空,這時候就需要手動映射了。
1.2 ResultMap手動映射⚡️
在UserMapper.xml修改如下,添加ResultMap
(resultMap標籤中的type可使用alias設置的類別名)
<resultMap id="UserMap" type="com.piao.pojo.User">
<!-- id爲主鍵 -->
<id column="id" property="id"/>
<!-- column是數據庫表的列名 , property是對應實體類的屬性名 -->
<result column="name" property="name"/>
<result column="pwd" property="password"/>
</resultMap>
<select id="selectUser" resultMap="UserMap">
select id,name,pwd from user
</select>
select標籤中的 resultType=“com.piao.pojo.User” 就可以替換成 resultMap="UserMap"
再次測試查詢所有用戶,結果如下:
User{id=2, name='張三', password='abcdef'}
User{id=3, name='李四', password='987654'}
User{id=5, name='趙六', password='13100'}
2.MyBatis與日誌
MyBatis日誌作用:如果一個 數據庫相關的操作出現了問題,我們可以根據輸出的SQL語句快速排查問題。
Mybatis內置的日誌工廠提供日誌功能,具體的日誌實現有以下幾種工具:
- SLF4J
- Apache Commons Logging
- Log4j 2
- Log4j
- JDK logging
具體選擇哪個日誌實現工具由MyBatis的內置日誌工廠確定。它會使用最先找到的(按上文列舉的順序查找)。如果一個都未找到,日誌功能就會被禁用。
2.1 導入log4j依賴:
<dependency>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
<version>1.2.17</version>
</dependency>
2.2 編寫配置文件log4j.properties
詳細可參考這位大佬的博客
在應用的類路徑中創建一個名爲 log4j.properties
的文件,文件的具體內容如下:
# 全局日誌配置
log4j.rootLogger=ERROR, stdout
# MyBatis 日誌配置
log4j.logger.com.piao.dao.BlogMapper=TRACE
# 控制檯輸出
log4j.appender.stdout=org.apache.log4j.ConsoleAppender
log4j.appender.stdout.layout=org.apache.log4j.PatternLayout
log4j.appender.stdout.layout.ConversionPattern=%5p [%t] - %m%n
#上述配置將使 Log4J 詳細打印 com.piao.dao.BlogMapper 的日誌,對於應用的其它部分,只打印錯誤信息。
#會將SQL打印到控制檯
2.3在mybatis-config.xml 配置日誌
<settings>
<setting name="logImpl" value="LOG4J"/>
</settings>
配置文件規定的配置順序:
The content of element type “configuration” must match “(properties?,settings?,typeAliases?,typeHandlers?,objectFactory?,objectWrapperFactory?,reflectorFactory?,plugins?,environments?,databaseIdProvider?,mappers?)”.
所以settings應該寫在properties之後。
2.4 使用log4j在Java中輸出日誌信息
導包:import org.apache.log4j.Loggerstatic
實例化Logger Logger logger = Logger.getLogger(MyTest.class);
使用logger輸出不同級別的日誌
- logger.info(“info:xxxx”);
- logger.debug(“debug:xxxxx”);
- logger.error(“error: xxxxx”);
之後便可在控制檯或者配置好的日誌文件中看到輸出的日誌信息。
3.分頁的多種實現方式
分頁查詢目的:緩解數據庫壓力(數據庫),提升用戶體驗(前端顯示)
3.1 SQL語句實現分頁(limit關鍵字)
可參考之前的MySQL筆記: MySQL學習筆記(5)——JOIN聯表查詢,自連接查詢,分頁和排序,子查詢與嵌套查詢
- LIMIT 起始值,每頁的大小
--下標從0開始 LIMIT 0,3 [0,3)即0,1,2 不包括3
-- 分頁 每頁3個
SELECT majorname,number FROM major LIMIT 2; -- 前兩個條數據
SELECT majorname,number FROM major LIMIT 0,3; -- 第一頁 第一1到第三3條數據
SELECT majorname,number FROM major LIMIT 3,3; -- 第二頁 第一4到第一6條數據
SELECT majorname,number FROM major LIMIT 6,3; -- 第三頁 第一7到第一9條數據
-- 查詢某條數據之後的所有數據,可指定第二數爲-1
SELECT * FROM table LIMIT 10,-1; // 檢索記錄行 下標爲10的數據到最後一條
-- LIMIT n 等價於 LIMIT 0,n。
公式:SELECT 字段 FROM 表 ... LIMIT (n-1)*pageSize,pageSize
- 參數:n:當前頁
- pagesize:頁面大小
- (n-1)*pageSize:起始值
- 總頁數=數據總數/頁面大小
這樣的分頁,需要傳遞兩個參數:開始的下標startIndex和頁面大小pageSize
mapper接口(片段)
//選擇全部用戶實現分頁
List<User> selectUser(Map<String,Integer> map);
UserMapper.xml(片段)
<select id="selectUser" parameterType="map" resultType="user">
select * from user limit #{startIndex},#{pageSize}
</select>
測試:
起始下標startIndex = (currentPage-1)*pageSize
int currentPage = 1; //第幾頁
int pageSize = 2; //頁面大小
Map<String,Integer> map = new HashMap<String,Integer>();
map.put("startIndex",(currentPage-1)*pageSize);
map.put("pageSize",pageSize);
List<User> users = mapper.selectUser(map);
查詢第n頁時,currentPage傳遞n即可。
3.2 MyBatis中Sqlsession+RowBounds實現分頁(不推薦用)
瞭解即可
UserMapper接口(片段)
//選擇全部用戶實現分頁
List<User> getUserByRowBounds();
UserMapper.xml(片段) 直接查詢所有
<select id="getUserByRowBounds"resultType="user">
select * from user;
</select>
獲取sqlsession後測試UserMapper接口
int currentPage = 2; //第幾頁
int pageSize = 2; //每頁顯示幾個
RowBounds rowBounds = new RowBounds((currentPage-1)*pageSize,pageSize);
//通過session.**方法進行傳遞rowBounds,[此種方式現在已經不推薦使用了]
List<User> users = sqlsession.selectList("com.piao.mapper.UserMapper.getUserByRowBounds", null, rowBounds);
3.3 第三方插件PageHelper(推薦使用⚡️)
官方網址: https://pagehelper.github.io/
官方教程(很詳細!👍): https://pagehelper.github.io/docs/howtouse/