很長時(shí)間沒更新了,最近換了一家公司,數(shù)據(jù)庫方面也從原先的 sqlserver 變成了麻煩一匹的 Oracle ,既然使用了 Oracle 那肯定或多或少的會(huì)遇到一些莫名其妙的問題。除了 Oracle 很多獨(dú)特的語法之外,還有一些奇怪的規(guī)則,比如我的標(biāo)題。
遇到問題的過程是這樣的,我在調(diào)試一體機(jī)的時(shí)候一體機(jī)掃描圖片之后不是存圖片路徑,而是把圖片轉(zhuǎn)換成 Base 64 的字符串格式存到數(shù)據(jù)庫中,這中奇葩方式真的是沒有見過,不過一體機(jī)不是我們這邊做的,我也沒辦法改變。所以只能適應(yīng)。在一開始測試的時(shí)候,我用的測試數(shù)據(jù)長度很短,所以在存入的時(shí)候沒有問題,但是后來前端給我傳來的真實(shí)數(shù)據(jù)存不進(jìn)去報(bào)錯(cuò)的時(shí)候,著實(shí)蒙了一比。后來經(jīng)過瀏覽各種帖子,最后還是解決了這個(gè)問題。
在貼代碼之前,有幾點(diǎn)要注意:
1.在存 Base 64 的時(shí)候,雖然也是字符串,但是由于長度過大,在 Oracle 中我們常用的 Varchar2 類型是存不進(jìn)去的,該類型只能存長度在 4000 以內(nèi)的數(shù)據(jù),所以我使用了 CLOB 類型
2.存 CLOB 類型的時(shí)候不能直接使用 sql 語法,而是要使用 Oracle 的參數(shù)綁定的方式

上圖是我使用的第一版本代碼,然后在第一次實(shí)際數(shù)據(jù)測試的時(shí)候華麗麗的報(bào)錯(cuò)了。報(bào)錯(cuò)是字符換長度過長。仔細(xì)觀看傳參,不是參數(shù)的錯(cuò)誤。然后直接復(fù)制代碼以及傳參到 plsql 中直接執(zhí)行,發(fā)現(xiàn)還是報(bào)錯(cuò),后來在網(wǎng)上查詢各種解答,明白了,原來是在單引號(hào)之間的字符串長度超過了 4000 。這跟 Varchar2 類型的長度上限是不同的。Varchar2 是因?yàn)楸臼≈荒艽?4000 以內(nèi)的字符串,但是這次報(bào)錯(cuò)的原因是因?yàn)閮蓚€(gè)單引號(hào)之間的字符串不能超過 4000 。
找到病因,接下來就是對癥下藥,既然一次存不下那么多,(順便說一下,我傳的數(shù)據(jù)長度是 11w7k 左右)那就拆開存就成了,遇事下面的版本新鮮出爐:

請忽略塊注釋標(biāo)題,,,。這次我的想法是首先在程序里把 11w7k 的數(shù)據(jù)拆分成 4000 一組的。然后統(tǒng)計(jì)出一共多少組,然后循環(huán)。就是先:數(shù)據(jù)長度/4000取整數(shù),然后數(shù)據(jù)長度%4000如果不等于0就在上面的取整數(shù)+1。然后前 4000 個(gè)字符是新增一條數(shù)據(jù),之后的 29 組全是在第一組的基礎(chǔ)上更新。
但是因?yàn)闃I(yè)務(wù)的需求,需要把多種材料的的掃描件一起存到數(shù)據(jù)庫里邊去,這樣一個(gè)材料存30次,10個(gè)材料就是200次,于是在實(shí)際數(shù)據(jù)測試的時(shí)候又華麗麗的炸了。
最后因?yàn)闃I(yè)務(wù)需求,我放棄了循環(huán)存入的方式,再一次閱讀網(wǎng)上帖子和文檔,最后確定了下面這一版。

同樣是數(shù)據(jù)綁定的方式,但是因?yàn)閍sp程序內(nèi)是沒有 4000 上限的規(guī)則的。于是我就可以通過設(shè)定參數(shù)類型的方式直接一次性將 11w+ 的數(shù)據(jù)長度一次性全部存進(jìn)去(這么簡單的方法為什么我一開始沒有找到)。
至此,本次問題完美解決。最后容我吐槽一下 Oracle 這數(shù)據(jù)庫。
新手一個(gè),如有錯(cuò)誤請留言,多交流