国产 无码 综合区,色欲AV无码国产永久播放,无码天堂亚洲国产AV,国产日韩欧美女同一区二区

MybatisPlus 使用 saveOrUpdate 詳解(慎用),及問題解決方法&mysql保存或更新 ON DUPLICATE KEY UPDATE

這篇具有很好參考價值的文章主要介紹了MybatisPlus 使用 saveOrUpdate 詳解(慎用),及問題解決方法&mysql保存或更新 ON DUPLICATE KEY UPDATE。希望對大家有所幫助。如果存在錯誤或未考慮完全的地方,請大家不吝賜教,您也可以點(diǎn)擊"舉報違法"按鈕提交疑問。

今天的想法是,要在插入數(shù)據(jù)庫時,如果有某某一個主要字段的值重復(fù),則不插入,否則則插入!
看了一下mybatis-Plus是有這個saveOrUpdate 方法!

原本使用save時是沒有問題了,改成saveOrUpdate 用了一下就報錯了。

com.baomidou.mybatisplus.core.exceptions.MybatisPlusException: error: can not execute. because can not find column for id from entity!

就是這個mybatisPlus不能找到哪個是主鍵字段,因?yàn)檫@個saveOrUpdate默認(rèn)是根據(jù)主鍵執(zhí)行操作的!

所有需要在原本的實(shí)體類的主鍵頭上,打個@TableId,如下,后面是對應(yīng)數(shù)據(jù)庫的字段,已經(jīng)主鍵自動遞增。

@Data
@AllArgsConstructor
@NoArgsConstructor
public class Subject {

  @TableId(value = "subject_Code", type = IdType.AUTO)
  private long subjectCode;

  private String subjectNameCn;

  private String subjectNameEn;

  private String subjectHref;

  private long subjectParentCode;

  private long levelCode;

  private int isDelete;

  private long operateTimestamp;


}

不過還有個問題,就是這個是根據(jù)主鍵做操作的,但是我主鍵本來就是自動遞增肯定不會有問題的,接下來就是想個辦法,讓他根據(jù)指定字段做操作,好像是有提供了一個口子。

// 根據(jù)updateWrapper嘗試更新,否繼續(xù)執(zhí)行saveOrUpdate(T)方法
boolean saveOrUpdate(T entity, Wrapper<T> updateWrapper);

我再去看一下怎么操作的!

研究嘗試了半天,終于搞出來了,可能是很少有人會像我這樣做吧!所以我自己嘗試了下。

當(dāng)saveOrUpdate不使用條件構(gòu)造器時,會先做根據(jù)主鍵查詢,如果查出來的結(jié)果為0,那么就執(zhí)行插入操作,如果查出來的結(jié)果不為0,則執(zhí)行更新操作。

但是一般情況下,主鍵都不會重復(fù)啊!所有我就用條件構(gòu)造器Wrapper!

UpdateWrapper<Subject> subject_name_cn = new UpdateWrapper<Subject>()
			.eq("subject_Name_Cn", subjectNameCn);
subjectService.saveOrUpdate(subject,subject_name_cn );

這樣改變后的結(jié)果就是會先執(zhí)行修改,如果執(zhí)行一條,則執(zhí)行成功,如果執(zhí)行結(jié)果為0,再執(zhí)行根據(jù)主鍵查詢,然后做插入操作!

其實(shí)有點(diǎn)多此一舉的感覺,因?yàn)榧热欢家呀?jīng)更新不到結(jié)果了,那么肯定是沒有這個字段咯!

不過轉(zhuǎn)念一想,你是指定字段沒有,又不是主鍵沒有!

但是主鍵自增那肯定沒有??!

所有我又想到一個騷操作,我不傳UpdateWrapper而傳QueryWrapper會怎么樣呢!

會不會加在查詢條件種呢!我丟進(jìn)去沒有報錯,有點(diǎn)小激動,不知道結(jié)果如何!

QueryWrapper<Subject> subject_name_cn1 = new QueryWrapper<Subject>()
                    .eq("subject_Name_Cn", subjectNameCn);
subjectService.saveOrUpdate(subject,subject_name_cn1);

好吧!上來全給我Update了!絲毫不留情面!我把數(shù)據(jù)刪了再試試!

好吧!然并卵!幻想破滅!跟傳UpdateWrapper沒有區(qū)別!~告辭!

看了一下源碼,默認(rèn)參數(shù)是Wrapper類型,然后根據(jù)條件構(gòu)造器更新,

成功則返回,

不成功則走無條件構(gòu)造器的方法。

default boolean saveOrUpdate(T entity, Wrapper<T> updateWrapper) {
    return this.update(entity, updateWrapper) || this.saveOrUpdate(entity);
}

我感覺應(yīng)該加個類型判斷!

 if(updateWrapper instanceof QueryWrapper){
 	去拼接查詢語句!
 }
  if(updateWrapper instanceof UpdateWrapper){
 	去拼接更新語句!
 }

這樣就不會只根據(jù)ID來死查了!


我才終于明白~

為什么要用updateWrapper了!

它與queryWrapper的區(qū)別就是。

updateWrapper用set來設(shè)置修改的數(shù)據(jù)。

queryWrapper應(yīng)用select來設(shè)置要查出來的數(shù)據(jù)。

哈哈,這個還是很重要的!


saveOrUpdate 是否有映射id

我們知道m(xù)ybatis在插入時,會映射id,但是如果是saveOrUpdate會怎么樣呢?

比如我saveOrUpdate()后,需要用他的id,但是我傳進(jìn)去的對象是沒有id的。

 @Test
 void saveOrUpdate(){
       UserText userText = new UserText();
       userText.setUserSex(Sex.MAN);
       boolean b = userTextService.saveOrUpdate(userText);
       System.out.println(userText.getUserId());
   }

可以看到他先通過id查了沒有再進(jìn)行插入,然后返回新的id。

==>  Preparing: SELECT user_id,user_name,user_sex,start_time FROM user_text WHERE user_id=?
==> Parameters: 0(Long)
<==      Total: 0
Releasing transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@6d0fe80c]
Fetched SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@6d0fe80c] from current transaction
==>  Preparing: INSERT INTO user_text ( user_sex ) VALUES ( ? )
==> Parameters: 1(Integer)
<==    Updates: 1

不過這個update,不用試我都感覺難搞,因?yàn)槟闳绻麤]有id,那么你傳入這個對象的值,可能查出多個對象,那么他要把哪個id映射回來,是吧!

@Test
void saveOrUpdate(){
     UserText userText = new UserText();
     userText.setUserSex(Sex.MAN);
     UpdateWrapper<UserText> objectUpdateWrapper = new UpdateWrapper<UserText>()
             .eq("user_sex",Sex.MAN);
     boolean b = userTextService.saveOrUpdate(userText,objectUpdateWrapper);
     System.out.println(userText.getUserId());
 }

但還是試一下,當(dāng)我們加了一個UpdateWrapper后,有執(zhí)行成功,執(zhí)行了3條,返回了id為0。

但是這次加了wrapper,我再試試如果只插入一條,會怎么樣。哈哈,不去讀源碼去debug,就只能這樣試試了,莫怪。

誒,對啊,我去看看源碼先,看能不能看出什么門道。

之前好像也有看了點(diǎn)源碼。兩種不同構(gòu)造的方法,執(zhí)行的邏輯也不一樣。

boolean saveOrUpdate(T entity);	

default boolean saveOrUpdate(T entity, Wrapper<T> updateWrapper) {
	return this.update(entity, updateWrapper) || this.saveOrUpdate(entity);
}

區(qū)別不大,就是會多執(zhí)行一步更新,如果執(zhí)行成功就直接走,執(zhí)行不成功再根據(jù)這個對象做saveOrUpdate。

進(jìn)去翻了翻就是,如果通過id查到值,就根據(jù)id更新,不然就做新增。

所以也就不用試了,還是自己手寫一個吧,如果需要返回id的話。

慎用!

細(xì)思極恐,當(dāng)你是主鍵自動生成的數(shù)據(jù),一定要寫UpdateWrapper,不然你必然是一直插入!完全不會更新,因?yàn)槟J(rèn)是用id查詢的。

而主鍵生成的數(shù)據(jù),一般都不會去寫一個id,所以?。≮s快看看吧!


UpdateWrapper 小貼士

上面雖然寫了updateWrapper可以寫一個set屬性,有兩種情況。

首先,我們一個對象,有5條屬性,只有4條有值,1條沒有值。

mybatis-plus在執(zhí)行時,會先去看看你的對象哪條屬性有值,哪條沒有。

只會更新有值的屬性,所以只會更新4個屬性,另外一個屬性并不會把他置空。

如果你只想改一條屬性,也可以多寫一個set,不過感覺沒啥必要,不過比較靈活的就是。
你想寫另外一個值,就可以寫進(jìn)set里。


2021-05-21 13:31:32

我發(fā)現(xiàn)一個很垃圾的,前面我吹的那個updateWrapper的set多牛逼,其實(shí)是我想的太美了,他只是在原本的基礎(chǔ)上再加一個字段!我吐了!

UpdateWrapper<GameScorePo> updateWrapper = new UpdateWrapper<GameScorePo>()
                   .eq("game_id",gameScorePo.getGameId())
                   .eq("team_id",gameScorePo.getTeamId())
                   .eq("quarter",gameScorePo.getQuarter())
                   .set("score",gameScorePo.getScore());

           gameScoreService.saveOrUpdate(gameScorePo,updateWrapper);

這樣的執(zhí)行結(jié)果是這樣的!

mybatisplus 保存或者更新,MyBatis-Plus,數(shù)據(jù)庫,MySQL,MybatisPlus,saveOrUpdate,保存或更新
兩個score,我吐了!

難道是我打開的姿勢不對?

查了一下知道這個set怎么樣了

mybatisplus 保存或者更新,MyBatis-Plus,數(shù)據(jù)庫,MySQL,MybatisPlus,saveOrUpdate,保存或更新
就是不要丟對象,丟一個空的對象,這樣就能set了!

單獨(dú)的set好用,但是用在saveOrUpdate就不好用咯!看自己的需求走吧!




INSERT INTO pms_statistic (
	id,
	tenantId,
	tenantName,
	isDeleted,
	createTime
)
VALUES
	(
		6257,50,'保存或修改0',1,'2020-01-00'
	) ,(
		6258,51,'保存或修改1',1,'2020-01-01'
	) ,(
		6259,52,'保存或修改2',1,'2020-01-02'
	) ,(
		62510,53,'保存或修改3',1,'2020-01-03'
	) 
ON DUPLICATE KEY UPDATE tenantId = VALUES(tenantId),tenantName = VALUES(tenantName)
		,isDeleted = VALUES(isDeleted),createTime = VALUES(createTime);

該語句是基于主鍵(PRIMARY KEY)或唯一索引(UNIQUE INDEX)使用的。
如果已存在該唯一標(biāo)示或主鍵就更新(顯示受影響行的值:2)

如果不存在該唯一標(biāo)示或主鍵則作為新行插入(顯示受影響行的值:1)

如上:如果id(6257,6258,6259,62510)存在,根據(jù)id更新ON DUPLICATE KEY UPDATE后的字段數(shù)據(jù)(tenantId = VALUES(tenantId),tenantName = VALUES(tenantName),isDeleted = VALUES(isDeleted),createTime = VALUES(createTime))

執(zhí)行sql前(存在6257id,其他id不存在)

執(zhí)行后

6257修改,6258,6259,62510插入

受影響行:5(插入3條,修改1條(修改是兩行))

注意:ON DUPLICATE KEY UPDATE只是MySQL的特有語法,并不是SQL標(biāo)準(zhǔn)語法!文章來源地址http://www.zghlxwxcb.cn/news/detail-679308.html

到了這里,關(guān)于MybatisPlus 使用 saveOrUpdate 詳解(慎用),及問題解決方法&mysql保存或更新 ON DUPLICATE KEY UPDATE的文章就介紹完了。如果您還想了解更多內(nèi)容,請?jiān)谟疑辖撬阉鱐OY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!

本文來自互聯(lián)網(wǎng)用戶投稿,該文觀點(diǎn)僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務(wù),不擁有所有權(quán),不承擔(dān)相關(guān)法律責(zé)任。如若轉(zhuǎn)載,請注明出處: 如若內(nèi)容造成侵權(quán)/違法違規(guī)/事實(shí)不符,請點(diǎn)擊違法舉報進(jìn)行投訴反饋,一經(jīng)查實(shí),立即刪除!

領(lǐng)支付寶紅包贊助服務(wù)器費(fèi)用

相關(guān)文章

  • MyBatisPlus解決邏輯刪除與唯一索引的兼容問題

    MyBatisPlus解決邏輯刪除與唯一索引的兼容問題

    比如有張用戶表,在插入或者更新數(shù)據(jù)的時候,我們需要 用戶名稱 (username),不能重復(fù)。 我們首先考慮的是給該字段創(chuàng)建唯一索引 似乎這樣就可以了,然而事情并沒有那么簡單。 因?yàn)槲覀儽碇械臄?shù)據(jù)在刪除的時候不會真的的刪除,而是采用邏輯刪除,會有一個 deleted 字段使用

    2023年04月13日
    瀏覽(32)
  • C語言移除元素問題解決方法詳解

    C語言移除元素問題解決方法詳解

    本文詳細(xì)介紹了解決移除元素問題的三種方法:暴力求解、空間換時間和雙指針方法,幫助讀者更好地理解和解決類似問題。

    2023年04月24日
    瀏覽(20)
  • MybatisPlus 超好用的idea代碼生成插件,及使用詳解

    MybatisPlus 超好用的idea代碼生成插件,及使用詳解

    文章目錄 前言 一、MybatisPlus簡介 二、MybatisPlus 代碼生成插件 1.插件安裝與配置 2.生成代碼結(jié)構(gòu)、內(nèi)容展示 3.表新增字段,重新生成實(shí)體類覆蓋? 總結(jié) 新需求來了,又添加了好幾張表,總不能手寫或者復(fù)制之前的代碼,再一通修改吧?! 一張表需要添加好幾個新字段,往實(shí)體

    2024年01月24日
    瀏覽(27)
  • MybatisPlus之QueryWrapper有無條件方法的使用說明

    QueryWrapper 兩種重載方法,其中一種是布爾類型condition條件參數(shù),另一種是沒有布爾類型參數(shù),比如下面這兩個方法: 它們有什么區(qū)別呢? 鄙人細(xì)研究了一番,得出如下結(jié)論: boolean condition:用于指定當(dāng)前這個條件是否有效;如果為 true,則使用當(dāng)前條件;如果為 false,則忽

    2024年02月12日
    瀏覽(24)
  • 解決‘getBaseMapper()‘ in ‘com.baomidou.mybatisplus.extension.service.impl.ServiceImpl‘ clashes with問題

    原因:包的問題 將 import com.baomidou.mybatisplus.mapper.BaseMapper; 改為 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; 即可

    2024年02月16日
    瀏覽(20)
  • 關(guān)于MyBatisPlus框架下出現(xiàn)xml里面定義的方法無法被正確識別以及提示調(diào)用mysql存儲過程時參數(shù)無效的問題

    關(guān)于MyBatisPlus框架下出現(xiàn)xml里面定義的方法無法被正確識別以及提示調(diào)用mysql存儲過程時參數(shù)無效的問題

    網(wǎng)上很多解決方法都是查看函數(shù)名是否一致、命名空間等,但還有一種可能是你調(diào)用接口的模塊本身的resource文件夾下就有一個含有xml的mapper文件夾,而這個文件夾里面不含有方法A的sql實(shí)現(xiàn),如下圖: 導(dǎo)致程序只在這個mapper里面找A的sql實(shí)現(xiàn),那肯定會提示沒有找到。 除了檢

    2024年02月09日
    瀏覽(29)
  • 【CAD卡頓解決方法詳解,網(wǎng)上最實(shí)用五種方法,開機(jī)卡頓,拖圖卡頓,畫直線卡頓等問題,一一詳細(xì)教你解決】

    【CAD卡頓解決方法詳解,網(wǎng)上最實(shí)用五種方法,開機(jī)卡頓,拖圖卡頓,畫直線卡頓等問題,一一詳細(xì)教你解決】

    我們剛裝好CAD時,往往會遇到啟動緩慢,畫直線卡頓等現(xiàn)象,接下來我就詳細(xì)介紹如何處理這些問題 面對啟動卡頓,我們可以將” 初始化界面 “給關(guān)閉掉,在命令行中輸入 StartMode 命令,將值設(shè)置為 0 設(shè)置完成后的啟動畫面如下 畫直線卡頓,往往是因?yàn)閯討B(tài)輸入沒有關(guān)閉,

    2024年02月16日
    瀏覽(15)
  • MybatisPlus使用Left Join...on...一對多多表聯(lián)查和Ipage分頁返回數(shù)據(jù)問題

    MybatisPlus使用Left Join...on...一對多多表聯(lián)查和Ipage分頁返回數(shù)據(jù)問題

    問題: 一對多關(guān)系表使用MybatisPlus的Ipage進(jìn)行分頁查詢,會先執(zhí)行聯(lián)表查詢sql語句,然后進(jìn)行分頁。 ?像圖中聯(lián)表查詢一對多關(guān)系,會有多條重復(fù)數(shù)據(jù),使用Ipage分頁會將這10條數(shù)據(jù)返回到xml中resultMap綁定的type。造成一頁展示的數(shù)據(jù)少于10條。 針對這種我們采用子查詢的方式解

    2024年02月13日
    瀏覽(21)
  • AprilTag的使用、相關(guān)問題及解決方法

    安裝標(biāo)定功能包 下載棋盤格 http://wiki.ros.org/camera_calibration/Tutorials/MonocularCalibration?action=AttachFiledo=viewtarget=check-108.pdf 啟動攝像頭 開始標(biāo)定 參數(shù)說明: size:????棋盤內(nèi)交叉點(diǎn)的個數(shù),行*列 square:??一個格子的邊長,單位是m image:??訂閱攝像頭發(fā)布的圖像話題(RO

    2024年02月10日
    瀏覽(19)
  • Hive使用中常見的問題及解決方法

    ????????Hive是基于Hadoop的一個數(shù)據(jù)倉庫工具,可以將結(jié)構(gòu)化的數(shù)據(jù)文件映射為一張表,并提供SQL查詢功能。在工作中大部分場景都會用到,下面列出幾個 hive 使用中常見的問題及解決方法。 1)Hive 默認(rèn)的輸入格式處理是CombineHiveInputFormat,會對小文件進(jìn)行合并 hive (default

    2024年02月10日
    瀏覽(18)

覺得文章有用就打賞一下文章作者

支付寶掃一掃打賞

博客贊助

微信掃一掃打賞

請作者喝杯咖啡吧~博客贊助

支付寶掃一掃領(lǐng)取紅包,優(yōu)惠每天領(lǐng)

二維碼1

領(lǐng)取紅包

二維碼2

領(lǐng)紅包