MyBatis中操作類對(duì)象的實(shí)現(xiàn)
Mapper.xml當(dāng)中的SQL標(biāo)簽都被解析成了一個(gè)一個(gè)的 MappedStatement對(duì)象。那么我們當(dāng)中的SQL是基于什么形式進(jìn)行封裝的呢?
在Java中,Java當(dāng)中一切皆對(duì)象。MappedStatement當(dāng)中SQL被封裝成了 MappedStatement 當(dāng)中的SqlSource對(duì)象。
我們通過(guò)sqlSource.getBoundSql()來(lái)獲取一個(gè)BoundSql對(duì)象,BoundSQL當(dāng)中的對(duì)象就是對(duì)于SQL語(yǔ)句的真實(shí)封裝。
Cofiguration 和 MappedStatement 存儲(chǔ)的是我們配置文件或者是在注解當(dāng)中書(shū)寫(xiě)的配置信息。它們是一個(gè)存儲(chǔ)對(duì)象。
我們還要有操作類型的對(duì)象。例如:在configuration中的mybatis-config.xml 和 我們的mapper的映射文件,xxxmapper.xml等配置文件。
1.什么是MyBatis操作類對(duì)象
在MyBatis框架中,操作類對(duì)象是用于執(zhí)行數(shù)據(jù)庫(kù)操作的核心對(duì)象。它是通過(guò)Mapper接口或者XML文件定義的,用于執(zhí)行與數(shù)據(jù)庫(kù)相關(guān)的CRUD操作(增刪改查)。
操作類對(duì)象的作用是提供一組方法,用于執(zhí)行數(shù)據(jù)庫(kù)操作并返回結(jié)果。這些方法可以是對(duì)應(yīng)于數(shù)據(jù)庫(kù)表的增刪改查操作,也可以是自定義的SQL查詢操作。
在MyBatis中,操作類對(duì)象有兩種定義方式:
- Mapper接口: 通過(guò)定義Java接口并使用注解或XML進(jìn)行映射,創(chuàng)建一個(gè)Mapper接口。Mapper接口中的方法可以通過(guò)注解或XML配置與具體的SQL語(yǔ)句進(jìn)行映射。開(kāi)發(fā)人員可以通過(guò)Java代碼直接調(diào)用接口中的方法來(lái)執(zhí)行數(shù)據(jù)庫(kù)操作。
- XML文件: 通過(guò)編寫(xiě)XML文件來(lái)定義SQL語(yǔ)句和數(shù)據(jù)庫(kù)操作,這些XML文件可以是獨(dú)立的SQL映射文件,也可以是Mapper接口對(duì)應(yīng)的XML配置文件。XML文件中定義了SQL語(yǔ)句的具體內(nèi)容和參數(shù)映射關(guān)系,開(kāi)發(fā)人員可以通過(guò)讀取和解析這些XML文件來(lái)執(zhí)行數(shù)據(jù)庫(kù)操作。
操作類對(duì)象可以通過(guò)MyBatis的Configuration對(duì)象或者SqlSessionFactory對(duì)象來(lái)獲取。一旦獲取到操作類對(duì)象,開(kāi)發(fā)人員就可以使用它提供的方法來(lái)執(zhí)行數(shù)據(jù)庫(kù)操作。操作類對(duì)象會(huì)將數(shù)據(jù)庫(kù)操作的細(xì)節(jié)封裝起來(lái),使開(kāi)發(fā)人員只需關(guān)注業(yè)務(wù)邏輯而不需要關(guān)心具體的SQL語(yǔ)句和數(shù)據(jù)庫(kù)連接操作。
總而言之,MyBatis操作類對(duì)象是用于執(zhí)行數(shù)據(jù)庫(kù)操作的核心對(duì)象,通過(guò)Mapper接口或者XML文件的定義,提供了一組方法來(lái)執(zhí)行與數(shù)據(jù)庫(kù)相關(guān)的增刪改查操作。它簡(jiǎn)化了數(shù)據(jù)庫(kù)操作的代碼編寫(xiě),提高了開(kāi)發(fā)效率和可維護(hù)性。
2.MyBatis操作類對(duì)象的分類
2.1 Executor
什么是Executor?
Excutor是執(zhí)行器的意思,什么是執(zhí)行器,執(zhí)行器就是完成各種操作的對(duì)象。Executor是執(zhí)行具體的SQL語(yǔ)句的核心組件之一。它負(fù)責(zé)接收Mapper接口或XML文件定義的SQL語(yǔ)句,并將其轉(zhuǎn)換為JDBC的PreparedStatement對(duì)象或Statement對(duì)象來(lái)執(zhí)行數(shù)據(jù)庫(kù)操作。
Executor主要有以下幾種分類:
2.1.1 BaseExecutor
- BaseExecutor :實(shí)現(xiàn)了Executor的全部方法,包括對(duì)緩存,事務(wù),連接提供了一系列的模板方法, 這些模板方法中留出來(lái)了四個(gè)抽象的方法等待子類去實(shí)現(xiàn)如下
protected abstract int doUpdate(MappedStatement ms, Object parameter) throws SQLException; protected abstract List<BatchResult> doFlushStatements(boolean isRollback) throws SQLException; protected abstract <E> List<E> doQuery(MappedStatement ms, Object parameter, RowBounds rowBounds, ResultHandler resultHandler, BoundSql boundSql) throws SQLException; protected abstract <E> Cursor<E> doQueryCursor(MappedStatement ms, Object parameter, RowBounds rowBounds, BoundSql boundSql) throws SQLException;
2.1.2 CachingExecutor
CachingExecutor是Executor的一種實(shí)現(xiàn),它的作用是提供緩存機(jī)制,用于緩存SQL語(yǔ)句的執(zhí)行結(jié)果。CachingExecutor會(huì)在執(zhí)行SQL語(yǔ)句之前先檢查緩存中是否存在相同的SQL語(yǔ)句及其參數(shù),如果存在,則直接從緩存中獲取結(jié)果,而不再執(zhí)行數(shù)據(jù)庫(kù)操作。
CachingExecutor的主要作用是提高系統(tǒng)的性能和響應(yīng)速度,避免對(duì)數(shù)據(jù)庫(kù)的頻繁訪問(wèn)。它可以減少與數(shù)據(jù)庫(kù)的交互次數(shù),降低數(shù)據(jù)庫(kù)的壓力,提高系統(tǒng)的吞吐量。
2.1.3 SimpleExecutor
SimpleExecutor是MyBatis默認(rèn)的Executor,它是在每次執(zhí)行SQL語(yǔ)句時(shí)創(chuàng)建一個(gè)新的Statement對(duì)象。它不支持事務(wù)處理,每次執(zhí)行SQL語(yǔ)句都會(huì)進(jìn)行數(shù)據(jù)庫(kù)連接的獲取和釋放。這種Executor適用于簡(jiǎn)單的、非事務(wù)性的SQL操作。
特點(diǎn)是每次執(zhí)行完畢后都會(huì)將創(chuàng)建出來(lái)的statement關(guān)閉掉,他也是默認(rèn)的執(zhí)行器類型。
SimpleExecutor是 MyBatis 提供的默認(rèn)的執(zhí)行器,他里面封裝了MyBatis對(duì)JDBC的操作,但是雖然他叫XXXExecuto,但是真正去CRUD的還真不是SimpleExecutor,先看一下它是如何重寫(xiě) BaseExecuto的doQuery()方法的
@Override public <E> List<E> doQuery(MappedStatement ms, Object parameter, RowBounds rowBounds, ResultHandler resultHandler, BoundSql boundSql) throws SQLException { Statement stmt = null; try { Configuration configuration = ms.getConfiguration(); StatementHandler handler = configuration.newStatementHandler(wrapper, ms, parameter, rowBounds, resultHandler, boundSql); stmt = prepareStatement(handler, ms.getStatementLog()); return handler.<E>query(stmt, resultHandler); } finally { closeStatement(stmt); } }
首先會(huì)創(chuàng)建StatementHandler
public StatementHandler newStatementHandler(Executor executor, MappedStatement mappedStatement, Object parameterObject, RowBounds rowBounds, ResultHandler resultHandler, BoundSql boundSql) { StatementHandler statementHandler = new RoutingStatementHandler(executor, mappedStatement, parameterObject, rowBounds, resultHandler, boundSql); statementHandler = (StatementHandler) interceptorChain.pluginAll(statementHandler); return statementHandler; }
雖然表面上看上面的代碼,感覺(jué)它只會(huì)創(chuàng)建一個(gè)叫 RoutingStatementHandler 的handler,但是其實(shí)上這里面有個(gè)秘密,根據(jù)MappedStatement 的不同,實(shí)際上他會(huì)創(chuàng)建三種不同類型的處理器,如下:
public RoutingStatementHandler(Executor executor, MappedStatement ms, Object parameter, RowBounds rowBounds, ResultHandler resultHandler, BoundSql boundSql) { switch (ms.getStatementType()) { case STATEMENT: delegate = new SimpleStatementHandler(executor, ms, parameter, rowBounds, resultHandler, boundSql); break; case PREPARED: delegate = new PreparedStatementHandler(executor, ms, parameter, rowBounds, resultHandler, boundSql); break; case CALLABLE: delegate = new CallableStatementHandler(executor, ms, parameter, rowBounds, resultHandler, boundSql); break; default: throw new ExecutorException("Unknown statement type: " + ms.getStatementType()); } }
最后通過(guò)closeStatement來(lái)關(guān)閉Statement
protected void closeStatement(Statement statement) { if (statement != null) { try { if (!statement.isClosed()) { statement.close(); } } catch (SQLException e) { // ignore } } }
2.1.4 ReuseExecutor
ReuseExecutor是Executor的一種實(shí)現(xiàn),它會(huì)重用已經(jīng)創(chuàng)建的Statement對(duì)象。它會(huì)對(duì)SQL語(yǔ)句進(jìn)行緩存,當(dāng)下次執(zhí)行相同的SQL語(yǔ)句時(shí),會(huì)直接使用已經(jīng)創(chuàng)建的Statement對(duì)象。這種Executor適用于相同SQL語(yǔ)句頻繁執(zhí)行的場(chǎng)景,可以減少Statement對(duì)象的創(chuàng)建和銷毀開(kāi)銷,提高性能。
在它在本地維護(hù)了一個(gè)容器,用來(lái)存放針對(duì)每條sql創(chuàng)建出來(lái)的statement,下次執(zhí)行相同的sql時(shí),會(huì)先檢查容器中是否存在相同的sql,如果存在就使用現(xiàn)成的,不再重復(fù)獲取。
應(yīng)用場(chǎng)景示例:
- 頻繁查詢靜態(tài)數(shù)據(jù):對(duì)于一些不經(jīng)常變化的靜態(tài)數(shù)據(jù),如國(guó)家、省份、城市等信息,可以使用CachingExecutor進(jìn)行緩存。這樣可以避免每次查詢都去數(shù)據(jù)庫(kù)中查詢,提高查詢效率。
- 頻繁查詢的結(jié)果集不變:對(duì)于一些業(yè)務(wù)場(chǎng)景中,某些查詢結(jié)果集在一段時(shí)間內(nèi)是不變的,如熱門商品、廣告信息等??梢允褂肅achingExecutor緩存這些查詢結(jié)果,減少數(shù)據(jù)庫(kù)的訪問(wèn)次數(shù),提高性能。
需要注意的是,CachingExecutor使用緩存機(jī)制可以提高性能,但同時(shí)也可能引入數(shù)據(jù)一致性的問(wèn)題。因?yàn)楫?dāng)對(duì)數(shù)據(jù)庫(kù)進(jìn)行增刪改操作時(shí),會(huì)導(dǎo)致緩存數(shù)據(jù)的失效。因此,在使用CachingExecutor時(shí),需要根據(jù)業(yè)務(wù)需求合理設(shè)置緩存的有效期,以保證數(shù)據(jù)的一致性。
在MyBatis中,默認(rèn)情況下是不開(kāi)啟CachingExecutor的,如果需要使用緩存機(jī)制,可以通過(guò)配置文件或注解來(lái)開(kāi)啟和配置緩存。
源碼解析:
這個(gè)ReuseExecutor相對(duì)于SimpleExecutor來(lái)說(shuō),不同點(diǎn)就是它先來(lái)的對(duì)Statement的復(fù)用,換句話說(shuō),某條Sql對(duì)應(yīng)的Statement創(chuàng)建出來(lái)后被放在容器中保存起來(lái),再有使用這個(gè)statement的地方就是容器中拿就行了
他是怎么實(shí)現(xiàn)的呢? 看看下面的代碼就知道了
public class ReuseExecutor extends BaseExecutor { private final Map<String, Statement> statementMap = new HashMap<String, Statement>(); public ReuseExecutor(Configuration configuration, Transaction transaction) { super(configuration, transaction); }
嗯! 所謂的容器,不過(guò)是一個(gè)叫statementMap的HashMap而已
下一個(gè)問(wèn)題: 這個(gè)容器什么時(shí)候派上用場(chǎng)呢? 看看下面的代碼也就知道了–this.hasStatementFor(sql)
private Statement prepareStatement(StatementHandler handler, Log statementLog) throws SQLException { Statement stmt; BoundSql boundSql = handler.getBoundSql(); String sql = boundSql.getSql(); if (hasStatementFor(sql)) { stmt = getStatement(sql); applyTransactionTimeout(stmt); } else { Connection connection = getConnection(statementLog); stmt = handler.prepare(connection, transaction.getTimeout()); putStatement(sql, stmt); } handler.parameterize(stmt); return stmt; }
最后一點(diǎn): 當(dāng)MyBatis知道發(fā)生了事務(wù)的提交,回滾等操作時(shí),ReuseExecutor會(huì)批量關(guān)閉容器中的Statement
2.1.5 BatchExecutor
BatchExecutor是Executor的一種實(shí)現(xiàn),它用于批量操作數(shù)據(jù)庫(kù)。它會(huì)將多個(gè)SQL語(yǔ)句進(jìn)行批量執(zhí)行,減少了與數(shù)據(jù)庫(kù)的交互次數(shù),提高了性能。BatchExecutor適用于需要批量插入、更新或刪除數(shù)據(jù)的場(chǎng)景。
特點(diǎn)是進(jìn)行批量修改,她會(huì)將修改操作記錄在本地,等待程序觸發(fā)提交事務(wù),或者是觸發(fā)下一次查詢時(shí),批量執(zhí)行修改。
2.2 StatementHandler
Statementhandler是四大神器中最重要的一個(gè)對(duì)象,負(fù)責(zé)操作Statement與數(shù)據(jù)庫(kù)進(jìn)行交流.在工作時(shí) 還會(huì)使用ParameterHandler進(jìn)行參數(shù)配置,使用ResultHandler將查詢結(jié)果與實(shí)體類對(duì)象進(jìn)行綁定。StatementHandler是MyBatis的核心組件之一,負(fù)責(zé)處理SQL語(yǔ)句的執(zhí)行和結(jié)果的映射。它是在執(zhí)行SQL語(yǔ)句之前進(jìn)行參數(shù)處理和SQL語(yǔ)句的構(gòu)建,然后執(zhí)行SQL語(yǔ)句,最后將結(jié)果映射到Java對(duì)象上。
StatementHandler的主要職責(zé)包括以下幾個(gè)方面:
- 參數(shù)處理:StatementHandler會(huì)將用戶傳入的參數(shù)與SQL語(yǔ)句中的占位符進(jìn)行匹配,構(gòu)建最終的可執(zhí)行的SQL語(yǔ)句。
- SQL語(yǔ)句的構(gòu)建:根據(jù)映射文件或注解中定義的SQL語(yǔ)句,StatementHandler會(huì)將參數(shù)替換為實(shí)際的值,生成最終的可執(zhí)行的SQL語(yǔ)句。
- SQL語(yǔ)句的執(zhí)行:StatementHandler將生成的SQL語(yǔ)句交給JDBC的Statement對(duì)象執(zhí)行,獲取執(zhí)行結(jié)果。
- 結(jié)果映射:StatementHandler將執(zhí)行結(jié)果映射到Java對(duì)象上,生成最終的結(jié)果。
StatementHandler的應(yīng)用場(chǎng)景:
- 執(zhí)行簡(jiǎn)單的SQL操作:StatementHandler適用于執(zhí)行簡(jiǎn)單的SQL操作,如查詢、插入、更新和刪除等。
- 自定義SQL語(yǔ)句:如果需要執(zhí)行的SQL語(yǔ)句不方便通過(guò)MyBatis的自動(dòng)映射機(jī)制來(lái)處理,可以使用StatementHandler來(lái)自定義SQL語(yǔ)句,實(shí)現(xiàn)更靈活的數(shù)據(jù)庫(kù)操作。
- 復(fù)雜的結(jié)果映射:如果需要將查詢結(jié)果映射到多個(gè)Java對(duì)象中,或者需要進(jìn)行一些特殊的結(jié)果處理,可以通過(guò)自定義StatementHandler來(lái)實(shí)現(xiàn)復(fù)雜的結(jié)果映射邏輯。
需要注意的是,大多數(shù)情況下,我們不需要直接操作和使用StatementHandler,MyBatis框架會(huì)自動(dòng)創(chuàng)建和管理StatementHandler對(duì)象。只有在需要實(shí)現(xiàn)一些特殊的數(shù)據(jù)庫(kù)操作時(shí),才需要自定義或擴(kuò)展StatementHandler。通常情況下,我們只需要編寫(xiě)Mapper接口或XML文件,定義SQL語(yǔ)句和結(jié)果映射規(guī)則,MyBatis會(huì)自動(dòng)處理和執(zhí)行SQL語(yǔ)句。
后續(xù)會(huì)繼續(xù)通過(guò)跟進(jìn)源碼分析…
2.3 ParameterHandler
ParameterHandler是MyBatis的核心組件之一,它負(fù)責(zé)處理SQL語(yǔ)句中的參數(shù)傳遞和設(shè)置。ParameterHandler主要用于將Java對(duì)象的屬性值設(shè)置到PreparedStatement中,替換SQL語(yǔ)句中的占位符。
ParameterHandler的主要職責(zé)包括以下幾個(gè)方面:
- 參數(shù)處理:ParameterHandler將用戶傳入的參數(shù)與SQL語(yǔ)句中的占位符進(jìn)行匹配,根據(jù)占位符的位置和類型,將Java對(duì)象的屬性值設(shè)置到PreparedStatement中。
- 參數(shù)類型處理:ParameterHandler負(fù)責(zé)處理不同類型的參數(shù),將Java對(duì)象的屬性值轉(zhuǎn)換為對(duì)應(yīng)的數(shù)據(jù)庫(kù)類型,以便正確地設(shè)置到PreparedStatement中。
- 參數(shù)傳遞:ParameterHandler將處理后的參數(shù)傳遞給JDBC的PreparedStatement對(duì)象,以便執(zhí)行SQL語(yǔ)句。
ParameterHandler的應(yīng)用場(chǎng)景:
- SQL語(yǔ)句的參數(shù)傳遞:ParameterHandler適用于處理SQL語(yǔ)句中的參數(shù)傳遞,將Java對(duì)象的屬性值設(shè)置到PreparedStatement中。這包括簡(jiǎn)單的參數(shù)類型,如字符串、整數(shù)、日期等,也包括復(fù)雜的參數(shù)類型,如Java對(duì)象、集合等。
- 動(dòng)態(tài)SQL語(yǔ)句的構(gòu)建:如果SQL語(yǔ)句是動(dòng)態(tài)生成的,根據(jù)不同的條件拼接不同的SQL片段,ParameterHandler可以根據(jù)條件設(shè)置對(duì)應(yīng)的參數(shù)值,確保動(dòng)態(tài)生成的SQL語(yǔ)句的正確執(zhí)行。
- 參數(shù)類型轉(zhuǎn)換:如果涉及到不同的數(shù)據(jù)類型,如Java對(duì)象屬性與數(shù)據(jù)庫(kù)字段類型不一致,或需要將Java對(duì)象屬性值轉(zhuǎn)換為數(shù)據(jù)庫(kù)支持的類型,ParameterHandler可以負(fù)責(zé)處理參數(shù)類型轉(zhuǎn)換,確保參數(shù)的正確性。
需要注意的是,大多數(shù)情況下,我們不需要直接操作和使用ParameterHandler,MyBatis框架會(huì)自動(dòng)創(chuàng)建和管理ParameterHandler對(duì)象。只有在需要實(shí)現(xiàn)一些特殊的參數(shù)處理或轉(zhuǎn)換操作時(shí),才需要自定義或擴(kuò)展ParameterHandler。通常情況下,我們只需要編寫(xiě)Mapper接口或XML文件,定義SQL語(yǔ)句和參數(shù)映射規(guī)則,MyBatis會(huì)自動(dòng)處理和設(shè)置參數(shù)。
后續(xù)會(huì)繼續(xù)通過(guò)跟進(jìn)源碼分析…
2.4 ResultSetHandler
ResultSetHandler是MyBatis的核心組件之一,它負(fù)責(zé)將JDBC查詢結(jié)果集中的數(shù)據(jù)映射到Java對(duì)象上。ResultSetHandler將ResultSet中的每一行數(shù)據(jù)轉(zhuǎn)換為Java對(duì)象,并將這些對(duì)象組成一個(gè)集合或數(shù)組,作為最終的查詢結(jié)果返回。
ResultSetHandler的主要職責(zé)包括以下幾個(gè)方面:
- 結(jié)果集處理:ResultSetHandler將JDBC的ResultSet對(duì)象中的數(shù)據(jù)進(jìn)行處理,將每一行數(shù)據(jù)轉(zhuǎn)換為Java對(duì)象。
- 映射規(guī)則:ResultSetHandler根據(jù)映射文件或注解中定義的結(jié)果映射規(guī)則,將ResultSet中的列與Java對(duì)象的屬性進(jìn)行映射。
- 數(shù)據(jù)類型轉(zhuǎn)換:ResultSetHandler負(fù)責(zé)將ResultSet中的數(shù)據(jù)轉(zhuǎn)換為Java對(duì)象的屬性類型,確保類型的匹配和正確性。
- 結(jié)果集的封裝:ResultSetHandler將處理后的Java對(duì)象封裝成一個(gè)集合或數(shù)組,作為最終的查詢結(jié)果返回給用戶。
ResultSetHandler的應(yīng)用場(chǎng)景:
- 查詢操作:ResultSetHandler適用于執(zhí)行查詢操作,將查詢結(jié)果映射到Java對(duì)象上,并返回給用戶。
- 數(shù)據(jù)類型轉(zhuǎn)換:如果查詢結(jié)果中的數(shù)據(jù)類型與Java對(duì)象的屬性類型不匹配,或者需要進(jìn)行一些特殊的數(shù)據(jù)類型轉(zhuǎn)換,ResultSetHandler可以負(fù)責(zé)處理數(shù)據(jù)類型的轉(zhuǎn)換,確保數(shù)據(jù)的正確映射。
- 結(jié)果集的定制化:如果需要將查詢結(jié)果映射到多個(gè)Java對(duì)象中,或者需要進(jìn)行一些特殊的結(jié)果處理,如對(duì)結(jié)果進(jìn)行分組、排序、聚合等,可以通過(guò)自定義ResultSetHandler來(lái)實(shí)現(xiàn)定制化的結(jié)果集處理邏輯。
需要注意的是,大多數(shù)情況下,我們不需要直接操作和使用ResultSetHandler,MyBatis框架會(huì)自動(dòng)創(chuàng)建和管理ResultSetHandler對(duì)象。只有在需要實(shí)現(xiàn)一些特殊的結(jié)果集處理邏輯時(shí),才需要自定義或擴(kuò)展ResultSetHandler。通常情況下,我們只需要編寫(xiě)Mapper接口或XML文件,定義SQL語(yǔ)句和結(jié)果映射規(guī)則,MyBatis會(huì)自動(dòng)處理和映射結(jié)果集。
后續(xù)會(huì)繼續(xù)通過(guò)跟進(jìn)源碼分析…
2.5 TypeHandler
TypeHandler是MyBatis的核心組件之一,它負(fù)責(zé)處理Java對(duì)象與數(shù)據(jù)庫(kù)類型之間的轉(zhuǎn)換。TypeHandler將Java對(duì)象的屬性值轉(zhuǎn)換為數(shù)據(jù)庫(kù)支持的數(shù)據(jù)類型,并且在從數(shù)據(jù)庫(kù)中讀取數(shù)據(jù)時(shí)將其轉(zhuǎn)換為Java對(duì)象的屬性類型。
TypeHandler的主要職責(zé)包括以下幾個(gè)方面:
- 參數(shù)設(shè)置:TypeHandler負(fù)責(zé)將Java對(duì)象的屬性值轉(zhuǎn)換為對(duì)應(yīng)的數(shù)據(jù)庫(kù)類型,將參數(shù)設(shè)置到PreparedStatement中。
- 結(jié)果獲取:TypeHandler負(fù)責(zé)從ResultSet中獲取數(shù)據(jù)庫(kù)的值,并將其轉(zhuǎn)換為Java對(duì)象的屬性類型。
- JDBC類型處理:TypeHandler根據(jù)Java對(duì)象的屬性類型和數(shù)據(jù)庫(kù)支持的類型,進(jìn)行類型之間的轉(zhuǎn)換,確保數(shù)據(jù)的正確性和兼容性。
TypeHandler的應(yīng)用場(chǎng)景:
- 自定義數(shù)據(jù)類型映射:如果在數(shù)據(jù)庫(kù)中使用了一些非標(biāo)準(zhǔn)或自定義的數(shù)據(jù)類型,TypeHandler可以幫助我們將這些類型映射到Java對(duì)象的屬性類型上,實(shí)現(xiàn)數(shù)據(jù)庫(kù)類型與Java類型之間的轉(zhuǎn)換。
- 數(shù)據(jù)類型轉(zhuǎn)換:如果Java對(duì)象的屬性類型與數(shù)據(jù)庫(kù)字段類型不匹配,或者需要進(jìn)行一些特殊的數(shù)據(jù)類型轉(zhuǎn)換,TypeHandler可以負(fù)責(zé)處理數(shù)據(jù)類型的轉(zhuǎn)換,確保數(shù)據(jù)的正確映射。
- 復(fù)雜數(shù)據(jù)結(jié)構(gòu)的映射:如果Java對(duì)象的屬性是一個(gè)復(fù)雜的數(shù)據(jù)結(jié)構(gòu),如JSON字符串、XML字符串等,TypeHandler可以負(fù)責(zé)將這些復(fù)雜結(jié)構(gòu)轉(zhuǎn)換為數(shù)據(jù)庫(kù)支持的數(shù)據(jù)類型,以及從數(shù)據(jù)庫(kù)中讀取并轉(zhuǎn)換為Java對(duì)象的屬性類型。
- 枚舉類型的映射:MyBatis內(nèi)置了一些常用的TypeHandler,可以直接映射Java的枚舉類型到數(shù)據(jù)庫(kù)中的數(shù)字或字符串類型。
需要注意的是,MyBatis提供了一些內(nèi)置的TypeHandler,用于處理常見(jiàn)的數(shù)據(jù)類型轉(zhuǎn)換,如字符串、整數(shù)、日期等。對(duì)于自定義的數(shù)據(jù)類型,我們可以通過(guò)實(shí)現(xiàn)TypeHandler接口來(lái)自定義TypeHandler,并注冊(cè)到MyBatis的配置中。這樣,在執(zhí)行SQL語(yǔ)句時(shí),MyBatis就會(huì)自動(dòng)調(diào)用相應(yīng)的TypeHandler來(lái)進(jìn)行數(shù)據(jù)類型的轉(zhuǎn)換。
后續(xù)會(huì)繼續(xù)通過(guò)跟進(jìn)源碼分析…
3.總結(jié)
到此這篇關(guān)于MyBatis中操作類對(duì)象的實(shí)現(xiàn)的文章就介紹到這了,更多相關(guān)MyBatis 操作類對(duì)象內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
java實(shí)現(xiàn)點(diǎn)擊按鈕事件彈出子窗口
這篇文章主要為大家詳細(xì)介紹了java實(shí)現(xiàn)點(diǎn)擊按鈕事件彈出子窗口,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2019-07-07使用Spring CROS解決項(xiàng)目中的跨域問(wèn)題詳解
這篇文章主要介紹了使用Spring CROS解決項(xiàng)目中的跨域問(wèn)題詳解,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2020-01-01springcloud?如何解決微服務(wù)之間token傳遞問(wèn)題
這篇文章主要介紹了springcloud?如何解決微服務(wù)之間token傳遞問(wèn)題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2022-03-03java實(shí)現(xiàn)的新浪微博分享代碼實(shí)例
這篇文章主要介紹了java實(shí)現(xiàn)的新浪微博分享代碼實(shí)例,是通過(guò)新浪API獲得授權(quán),然后接受客戶端請(qǐng)求的數(shù)據(jù),第三方應(yīng)用發(fā)送請(qǐng)求消息到微博,喚起微博分享界面,非常的實(shí)用,有相同需要的小伙伴可以參考下。2015-03-03