關(guān)于Oracle數(shù)據(jù)庫LOB大字段總結(jié)
在ORACLE數(shù)據(jù)庫中,DBA_OBJECTS視圖中OBJECT_TYPE為LOB的對象是什么東西呢?其實OBJECT_TYPE為LOB就是大對象(LOB),它指那些用來存儲大量數(shù)據(jù)的數(shù)據(jù)庫字段。
Oracle 11gR2 文檔:
http://download.oracle.com/docs/cd/E11882_01/appdev.112/e18294/adlob_tables.htm#ADLOB45267
一、LOB 分類
LOB大對象主要是用來存儲大量數(shù)據(jù)的數(shù)據(jù)庫字段,在Oracle 9iR2 中LOB的最大容量是4G,Oracle 10g 最大8T,Oracle 11g 最大是128T。具體取決于blocksize 的大小。
The built-in LOB data types BLOB, CLOB, and NCLOB (stored internally) and BFILE (stored externally) can store large and unstructured data such as text, image, video, and spatial data. The size of BLOB, CLOB, and NCLOB data can be up to (232-1 bytes) * (the value of the CHUNK parameter of LOB storage). |
1. Oracle 支持4 種類型的LOB:
- CLOB:字符LOB。這種類型用于存儲大量的文本信息,如XML 或者只是純文本。這個數(shù)據(jù)類型需要進行字符集轉(zhuǎn)換,也就是說,在獲取時,這個字段中的字符會從數(shù)據(jù)庫的字符集轉(zhuǎn)換為客戶的字符集,而在修改時會從客戶的字符集轉(zhuǎn)換為數(shù)據(jù)庫的字符集。
- NCLOB:這是另一種類型的字符LOB。存儲在這一列中的數(shù)據(jù)所采用的字符集是數(shù)據(jù)庫的國家字符集,而不是數(shù)據(jù)庫的默認字符集。
- BLOB:二進制LOB。這種類型用于存儲大量的二進制信息,如字處理文檔,圖像和你能想像到的任何其他數(shù)據(jù)。它不會執(zhí)行字符集轉(zhuǎn)換。應(yīng)用向BLOB 中寫入什么位和字節(jié),BLOB就會返回什么為和字節(jié)。
- BFILE:二進制文件LOB。這與其說是一個數(shù)據(jù)庫存儲實體,不如說是一個指針。帶BFILE列的數(shù)據(jù)庫中存儲的只是操作系統(tǒng)中某個文件的一個指針。這個文件在數(shù)據(jù)庫之外維護,根本不是數(shù)據(jù)庫的一部分。BFILE 提供了文件內(nèi)容的只讀訪問。
2. LOB數(shù)據(jù)類型分類
(1) 按存儲數(shù)據(jù)的類型分:
字符類型:
- CLOB:存儲大量 單字節(jié) 字符數(shù)據(jù)。
- NLOB:存儲定寬 多字節(jié) 字符數(shù)據(jù)。
二進制類型:
- BLOB:存儲較大無結(jié)構(gòu)的二進制數(shù)據(jù)。
二進制文件類型:
- BFILE:將二進制文件存儲在數(shù)據(jù)庫外部的操作系統(tǒng)文件中。存放文件路徑。
(2) 按存儲方式分:
- 存儲在內(nèi)部表空間(內(nèi)部LOB):CLOB,NLOB和BLOB
- 指向外部操作系統(tǒng)文件(外部LOB):BFILE
二、Lob的存儲
我們建立含有l(wèi)ob字段的表時,oracle會自動為lob字段建立兩個單獨的segment,一個用來存放數(shù)據(jù),另一個用來存放索引,并且它們都會存儲在對應(yīng)表指定的表空間中。
如上例所示,每個lob字段都對應(yīng)兩個segment,其中存放lob數(shù)據(jù)的以SYS_LOB開頭,存放索引以SYS_IL開頭。
LOB 按“塊”(chunk)或(piece)來存儲,每個片段都可以訪問。
三、Lob與其它類型的轉(zhuǎn)換
通過TO_CLOB可以將CHAR,NCHAR,VARCHAR2,NVARCHAR2,NCLOB類型轉(zhuǎn)換成CLOB;
通過TO_LOB可以將LONG RAW轉(zhuǎn)換成BLOB,LONG轉(zhuǎn)換成CLOB;
通過TO_NCLOB可以將CHAR,NCHAR,VARCHAR2,NVARCHAR2,CLOB轉(zhuǎn)換成NCLOB。
四、Oracle數(shù)據(jù)庫的SYS_LOB
看看你的表里是不是存在blog,clob等類型的字段,當我們所建立的表中含有l(wèi)ob型的數(shù)據(jù)時,oracle會為每個lob字段生成一個獨立的segment用來存放數(shù)據(jù),同時也建立了獨立的index segment .oracle對它們是單獨管理的。
普通表只會新增一個或兩個段對象.類型為TABLE和INDEX,數(shù)據(jù)就存放在表段中.索引就放在索引段中。但是LOB列則額外新增了兩個段對象,類型為LOBSEGMENT和LOBINDEX,LOBINDEX用于指向LOB段,找出其中的某一部分,所以存儲在表中的LOB存儲的是一個地址,或者說是一個指針,實際上表中的lob列中存的是一個地址段.然后在lobindex找到所有的地址段.然后在lobSegment中把所有地址段的值都讀取了來。所以lobSegment就保存了LOG列的真正的數(shù)據(jù),所以會非常大,并且獨立于原始表存在。
先看看這個對應(yīng)的表的字段是否有數(shù)據(jù),如果有你就無法刪除這個sys_lob$的對象。想減少空間的占用就清理歷史數(shù)據(jù),或者重新導出導入下。
五、相關(guān)概念
關(guān)于LOB,我們可以使用dbms_metadata來獲得它的完整的腳本:
- SELECT DBMS_METADATA.GET_DDL( 'TABLE', 'LOB_TABLE' ) FROM DUAL
1. 表空間
保存lob數(shù)據(jù)的表空間可以不同于保存表數(shù)據(jù)的表空間,為LOB數(shù)據(jù)單獨使用一個表空間有利于備份和恢復以及空間管理但是lobindex和lobsegment必須在同一個表空間中
2. IN ROW
- ENABLE STORAGE IN ROW
- DISABLE STORAGE IN ROW
控制LOB數(shù)據(jù)是否總與表分開存儲(存儲在lobsegment中),或是有時可以與表一同存儲,而不用單獨放在lobsegment中。
如果設(shè)置了ENABLE STORAGE IN ROW,而不是DISABLE STORAGE IN ROW,小LOB(最多4,000字節(jié))就會像VARCHAR2一樣存儲在表本身中。只有當LOB超過了4,000字節(jié)時,才會“移出”到lobsegment中
默認行為是啟用行內(nèi)存儲ENABLE STORAGE IN ROW,如果lob存儲的數(shù)據(jù)大小能在表本身中放下,建議采用內(nèi)聯(lián)存儲
3. CHUNK
塊(chunk)是邏輯上連續(xù)的一組數(shù)據(jù)庫塊(block),這也是LOB的最小分配單元。,每個LOB實例(每個行外存儲的LOB值)會占用至少一個CHUNK。一個CHUNK有一個LOB值使用,每個chunk的大小應(yīng)該盡可能與實際lob數(shù)據(jù)的大小相近,以減少浪費空間;
4. PCTVERSION
控制lob的讀一致性。
PCTVERSION控制著用于實現(xiàn)LOB數(shù)據(jù)版本化的已分配LOB空間的百分比(這些數(shù)據(jù)庫塊由某個時間點的LOB所用,并處在lobsegment的HWM以下)。對于許多使用情況來說,默認設(shè)置12%就足夠了,因為在很多情況下,你只是要INSERT和獲取LOB(通常不會執(zhí)行LOB的更新;LOB往往會插入一次,而獲取多次)。因此,不必為LOB版本化預(yù)留太多的空間(甚至可以沒有)。
如果你的應(yīng)用確實經(jīng)常修改LOB,假設(shè)很頻繁地讀LOB,與此同時另外某個會話正在修改這些LOB,12%可能就太小了。如果處理LOB時遇到一個ORA-22924錯誤,解決方案不是增加undo表空間的大小,也不是增加undo保留時間(UNDO_RETENTION),如果你在使用手動undo管理,那么增加更多RBS空間也不能解決這個問題。而是應(yīng)該使用以下命令:
- ALTER TABLE tabname MODIFY LOB (lobname) ( PCTVERSION n)
增加lobsegment中為實現(xiàn)數(shù)據(jù)版本化所用的空間大小。
5. CACHE
控制lobsegment數(shù)據(jù)是否存儲在緩沖區(qū)緩存中。默認的NOCACHE指示,每個訪問都是從磁盤的一個直接讀
- ALTER TABLE tabname MODIFY LOB (lobname) ( CACHE );
- ALTER TABLE tabname MODIFY LOB (lobname) ( NOCACHE );
六、查看ORACLE的LOB(BLOB和CLOB)對象占用的大小
1. 查看Oracle中表空間及表數(shù)據(jù)大小
- Select Segment_Name, Sum(bytes) / 1024 / 1024
- From User_Extents
- where SEGMENT_NAME LIKE 'SYS_LOB%'
- GROUP BY Segment_Name
- order by Sum(bytes) / 1024 / 1024 desc;
從返回的結(jié)果看,有一個segment名為"SYS_LOB0000701017C00045$$"的對象占用了大量的空間,這種帶有SYS_LOB***即LOB(BLOB和CLOB)對象占用數(shù)據(jù)庫的空間名稱。
2. 根據(jù)segment_name,就可以從 dba_lobs 表里查到是哪個表,哪個字段
- SELECT * FROM DBA_LOBS WHERE SEGMENT_NAME LIKE 'SYS_LOB0000701017C00045$$';