oracle中的char和j,oracle中char与varchar2的区别
1.
CHAR的長(zhǎng)度是固定的,而VARCHAR2的長(zhǎng)度是可以變化的, 比如,存儲(chǔ)字符串“abc",對(duì)于CHAR
(20),表示你存儲(chǔ)的字符將占20個(gè)字節(jié)(包括17個(gè)空字符),在數(shù)據(jù)庫中它是以空格占位的,而同樣的VARCHAR2
(20)則只占用3個(gè)字節(jié)的長(zhǎng)度,20只是最大值,當(dāng)你存儲(chǔ)的字符小于20時(shí),按實(shí)際長(zhǎng)度存儲(chǔ)。
2.CHAR的效率比VARCHAR2的效率稍高。看來cscm_number應(yīng)該設(shè)成
char(19)
3.目前VARCHAR是VARCHAR2的同義詞。工業(yè)標(biāo)準(zhǔn)的VARCHAR類型可以存儲(chǔ)空字符串,但是Oracle不這樣做,盡管它保留以后這樣做的權(quán)利。Oracle自己開發(fā)了一個(gè)數(shù)據(jù)類型VARCHAR2,這個(gè)類型不是一個(gè)標(biāo)準(zhǔn)的VARCHAR,它將在數(shù)據(jù)庫中varchar列可以存儲(chǔ)空字符串的特性改為存儲(chǔ)NULL值。假如你想有向后兼容的能力,Oracle建議使用VARCHAR2而不是VARCHAR。
何時(shí)該用CHAR,何時(shí)該用varchar2?
CHAR與VARCHAR2是一對(duì)矛盾的統(tǒng)一體,兩者是互補(bǔ)的關(guān)系.
VARCHAR2比CHAR節(jié)省空間,在效率上比CHAR會(huì)稍微差一些,即要想獲得效率,就必須犧牲一定的空間,這也就是我們?cè)跀?shù)據(jù)庫設(shè)計(jì)上常說的‘以空間換效率’。
VARCHAR2雖然比CHAR節(jié)省空間,但是假如一個(gè)VARCHAR2列經(jīng)常被修改,而且每次被修改的數(shù)據(jù)的長(zhǎng)度不同,這會(huì)引起‘行遷移’(Row
Migration)現(xiàn)象,而這造成多余的I/O,是數(shù)據(jù)庫設(shè)計(jì)和調(diào)整中要盡力避免的,在這種情況下用CHAR代替VARCHAR2會(huì)更好一些。
----以上內(nèi)容由?華夏名網(wǎng)?搜集整理,如轉(zhuǎn)載請(qǐng)注明原文出處,并保留這一部分內(nèi)容。
關(guān)于char和varchar2的比較的問題
關(guān)于char和varchar2的比較
char類型與char型或字符常量的比較,在比較時(shí)使用補(bǔ)齊空格的方式進(jìn)行比較。varchar2類型與varchar2類型,char型和字符常量的比較,在比較時(shí)不補(bǔ)充空格,直接比較。create table tt(A1 CHAR(2) , A2 VARCHAR2(2)) ;
INSERT INTO TT VALUES('A','A') ;
insert into tt values('A','A ') ;
COMMIT ;
--CHAR型與字符常量的比較,字符常量作為char型處理
--與'A'比較,返回2行,也就是在比較時(shí)自動(dòng)將常量'A'右補(bǔ)齊空格后比較
select * from tt where a1='A' ;
A1 A2
-- --
A?A
A?A
--與'A '比較,返回2行,也就是在比較時(shí)自動(dòng)將常量'A'右補(bǔ)齊空格后比較
select * from tt where a1='A ' ;
A1 A2
-- --
A?A
A?A
--VARCHAR2與常量的比較,字符常量作為varchar2型處理--與'A'比較,返回1行,也就是在比較時(shí)對(duì)'A'不做處理,直接比較
select?* from TT WHERE A2='A';
A1 A2
-- --
A?A
--與'A '比較,返回1行,也就是在比較時(shí)對(duì)'A'不做處理,直接比較
select?* from TT WHERE A2='A ';
A1 A2
-- --
A?A
--當(dāng)CHAR類型和VARCHAR2類型比較時(shí),比較時(shí)對(duì)字段值是不作處理,直接比較的--讓A1和A2直接比較,此時(shí)是直接比較,有一條記錄的A1和A2相同
select * from tt where a1=a2 ;
A1 A2
-- --
A?A
但是當(dāng)和decode函數(shù)配合使用時(shí),出現(xiàn)不同的情況
使用A1字段
select?decode(a1,'A','AAAA','BBBB') FROM TT
;
DECODE(A1,'A','AAAA','BBBB')
----------------------------
BBBB
BBBB
雖然A1字段為char(2),但是比較時(shí)并沒有將常量'A'補(bǔ)空格再與字段A1做比較,而是直接進(jìn)行比較,也就是將兩個(gè)比較字段按照varchar2類型處理的因此比較時(shí)認(rèn)為字段A1不等于常量'A',出現(xiàn)兩條結(jié)果為'BBB'的記錄。
進(jìn)一步驗(yàn)證,
select?decode(a1,'A?','AAAA','BBBB') FROM TT ; --此處是兩個(gè)空格
DECODE(A1,'A','AAAA','BBBB')
----------------------------
BBBB
BBBB
還是返回兩條'BBB'的記錄,說明比較的不是按照char型的比較規(guī)則處理的。
使用A2字段
select?decode(a2,'A','AAAA','BBBB') FROM TT
;
DECODE(A2,'A','AAAA','BBBB')
----------------------------
AAAA
BBBB
此時(shí)是正常的VARCHAR2類型之間的比較,第一條記錄的A2字段等于'A',返回'AAA',第二行記錄的A2字段為’A
',比較時(shí)不等,返回'BBB'
當(dāng)使用case表達(dá)式處理A1字段時(shí),出現(xiàn)了與decode函數(shù)不同的處理結(jié)果
使用字段A1
select?case a1 when 'A' then 'AAA' else 'BBB' end
from tt ;
CASEA1WHEN'A'THEN'AAA'ELSE'BBB
------------------------------
AAA
AAA
在使用case語句中使用A1字段與常量'A'比較時(shí),兩個(gè)比較值按照char型的比較規(guī)則處理,在右補(bǔ)空格之后進(jìn)行比較,因此返回兩條記錄
進(jìn)一步驗(yàn)證,如下,
select?case a1 when
'A?' then 'AAA' else 'BBB' end
from tt ;
CASEA1WHEN'A'THEN'AAA'ELSE'BBB
------------------------------
AAA
AAA
此時(shí)將常量改為'A?',比較時(shí)仍視為char類型之間的比較,將字段A1補(bǔ)齊空格后與常量比較。
使用A2字段
select?case a2 when 'A' then 'AAA' else 'BBB' end
from tt ;
CASEA2WHEN'A'THEN'AAA'ELSE'BBB
------------------------------
AAA
BBB
此時(shí)是正常的VARCHAR2類型之間的比較,第一條記錄的A2字段等于'A',返回'AAA',第二行記錄的A2字段為’A
',比較時(shí)不等,返回'BBB'
總結(jié),
在使用decode函數(shù)對(duì)char字段做比較時(shí),需要注意即使比較的兩個(gè)字段都是char類型,但是decode函數(shù)是將其轉(zhuǎn)化varchar2類型
進(jìn)行處理,不遵循char型的比較規(guī)則
===============================評(píng)論1============================
這幾天頻繁遇到char型數(shù)據(jù)比較的問題,總結(jié)如下:
對(duì)于char數(shù)據(jù),在集合操作中,按照char的實(shí)際數(shù)據(jù)進(jìn)行比較,而不是按照char型數(shù)據(jù)的比較規(guī)則進(jìn)行的。
下面是一個(gè)簡(jiǎn)單例子
create table t1(name char(10)) ;
create table t2(name char(20)) ;
begin
for i in 1..5 loop
insert into t1 values(to_char(i)) ;
insert into t1 values(to_char(i)) ;
end loop ;
commit;
end ;
select name from t1 minus select name from t2 ;
NAME
--------------------
1
2
3
4
5
如果按照char型的比較規(guī)則,則不應(yīng)該有返回值。
select anem from t1 intersect select name from t2 ;
NAME
--------------------
無返回值,也說明集合操作時(shí)比較沒有按照char型的比較規(guī)則。
===============================評(píng)論2============================
對(duì)于decode和case對(duì)于char類型的差別,原因是由于case是表達(dá)式,而decode是函數(shù)。
函數(shù)中輸入?yún)?shù)和返回值一般都定義為varchar2類型。
多謝指點(diǎn),一時(shí)沒有想到這里,看了一下decode函數(shù)的定義,如你所述,在使用decode的函數(shù)對(duì)char型數(shù)據(jù)進(jìn)行類型轉(zhuǎn)換。
下面是decode的函數(shù)的參數(shù)定義。
SQL> desc
sys.standard.decode
Parameter
Type?Mode Default?
--------- ----------------------- ---- --------
(RESULT)?NUMBER?EXPR?NUMBER?IN?PAT?NUMBER?IN?RES?NUMBER?IN(RESULT)?VARCHAR2?EXPR?NUMBER?IN?PAT?NUMBER?IN?RES?VARCHAR2?IN?(RESULT)?DATE?EXPR?NUMBER?IN?PAT?NUMBER?IN?RES?DATE?IN(RESULT)?NUMBER?EXPR?VARCHAR2?IN?PAT?VARCHAR2?IN?RES?NUMBER?IN(RESULT)?VARCHAR2
EXPR?VARCHAR2?IN
PAT?VARCHAR2?IN?RES?VARCHAR2?IN?(RESULT)?DATE?EXPR?VARCHAR2?IN?PAT?VARCHAR2?IN?RES?DATE?IN(RESULT)?NUMBER?EXPR?DATE?IN?PAT?DATE?IN?RES?NUMBER?IN?(RESULT)?VARCHAR2?EXPR
總結(jié)
以上是生活随笔為你收集整理的oracle中的char和j,oracle中char与varchar2的区别的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: oracle 唯一约束作用,想问下在表上
- 下一篇: soapui oracle groovy