在c語言中,對字串的操作主要有兩種方式,一是使用字元陣列,char str;二是使用字元指標。那麼二者有什麼區別呢?下面將分述二者的使用,最後進行比較。
一、字元陣列
使用char str定義乙個字元陣列str,中括號內可以寫上數字表示陣列大小,也可以不寫。如果不寫數字,則必須為字元陣列提供初始值,以便編譯器進行記憶體分配。
可以使用字串字面值(string literal)來初始化字元陣列,也可使用字元字面值(character literal)初始化,如:
[cpp]view plain
copy
? char
str1[10]=
"hello"
; char
str2=
"world"
; char
str3=;
只能對字元陣列元素的賦值,而不能用賦值語句對整個陣列賦值,如:
[cpp]view plain
copy
? char
str4[10];
str4=;
// 錯誤
str4="hello"
;
// 錯誤
str4[0]='h'
;str4[1]=
'e';str4[2]=
'l';str4[3]=
'l';str4[4]=
'o';
// 正確
可以使用迴圈將字元陣列中的字元乙個乙個輸出,也可以使用cout<
需要注意的是,上述**中str1和str2是c風格字串,而str3不是。c風格字串,是指以\0結尾的字元陣列。c++為了相容c,而保留了c中字串的使用方法。
str1和str2使用字串字面值進行初始化,字串字面值使用\0表示字串結束。因此str2長度為6,需要將\0計算在內。使用strlen函式,計算的是字串的實際長度,不包含\0。
而str3則不一樣,它沒有\0作為結束標誌,因而不是c風格字串,使用cout<
二、字元指標
可以使用char *str指向乙個字串。如:
[cpp]view plain
copy
? char
*ptr=
"c++"
; char
strarr=
"c++"
; char
*ptr2=strarr;
使用cout<
字元指標也可指向c風格字串,如ptr就是指向的c風格字串。如果讓ptr指向上節中的str3,輸出ptr會出現同樣的意想不到的結果。畢竟陣列名其實就是一種指標。
三、區別
前面簡單介紹了一下兩種操作字串的方法,這部分進行比較,是本文的重點。如下**:
[cpp]view plain
copy
? char
s="abc"
; char
*ptr=
"abc"
; coutcout<<*scout<<&scout<<(s+1)cout<<*(s+1)cout<<&s[1]coutcout<<*ptrcout<<&ptrcout<<(ptr+1)cout<<*(ptr+1)cout<<&ptr[1]這些**應該能夠說明char s和char *ptr之間的相似點了。它們都是指向字串的指標。
下面說二者的不同之處。如下一段**:
[cpp]view plain
copy
? char
ss="c++"
; ss[0]='c'
;
// 合法
char
*p="c++"
; p[0]='c'
;
// 合法但不正確
該段**在vs2010下編譯可以通過,但是執行時程式會停止工作,為什麼呢?原因在於p[0]='c'這一語句。該語句試圖修改p指向的字串的首個字元,出現了錯誤。
原因在於兩種方式對字元陣列操作的機制不同。使用char *p="c++"語句後,編譯器在記憶體的文字常量區分配一塊記憶體,儲存」c++「這一字串字面值,然後在棧上分配記憶體儲存p,p的內容為"c++"的位址。p[0]='c'試圖修改常量」c++「,程式當然就會崩潰了。而char ss="c++"語句,定義了乙個陣列,編譯器為其在棧上分配了記憶體空間,因而可以進行修改操作。
因此,可以總結如下:
(1)char ss定義了乙個陣列,ss可認為是乙個常指標,ss不可改變,但ss指向的內容可以發生改變。
(2)char *p定義了乙個可變指標,p可以指向其它物件。但對於char *p=」abc「這樣的情況,p指向的是常量,故內容不能改變。
如下**進一步說明char ss和char *p的區別:
[cpp]view plain
copy
? char
*stra()
呼叫該函式,不一定能夠得到正確的結果。因為str定義了乙個區域性資料,是區域性變數,存在於函式stra中的棧幀中。當函式呼叫完成後,棧幀恢復到函式stra呼叫前的狀態,臨時空間被重置,為函式分配的棧空間被收回,str所指向的位址也就不存在了。
將上述**修改:
[cpp]view plain
copy
? char
*stra()
該函式能夠正常執行,因為str指向的字串字面值被儲存在唯讀的資料段,是全域性的,當函式呼叫完成後,str指向的位址未發生變化。
綜上,可以看出使用char 較容易出錯,可能出現不確定的結果。c++提供的string類相比之下,要安全的多了。
參考自:
字元陣列和字元指標的區別分析
1.字元指標可以指向乙個字串。我們可以用字串常量對字元指標進行初始化。例如,有說明語句 char str this is a string.是對字元指標進行初始化。此時,字元指標指向的是乙個字串常量的首位址,即指向字串的首位址。這裡要注意字元指標與字元陣列之間的區別。例如,有說明語句 char st...
字元陣列和字元指標用法的區別
字元指標 char p,只可接收已知的字串字面量 字元陣列 char a 100 可接收已知或未知的字串。原理 字元指標只能儲存乙個字元型別的位址,而字串字面量表示式的返回值是 首元素首位址,所以字元指標可以獲得該首位址,並且可以通過指標讀取該字串,但不能修改,因為字串字面量都儲存在唯讀記憶體區域內...
指標與陣列 字元指標,字串和字元陣列的區別
指標和陣列是不相等的,把乙個陣列名作為乙個引數傳遞給函式時陣列名就是指向第乙個元素的指標,在大多數表示式中 陣列名的值是指向第乙個元素的指標 有兩個例外,乙個是sizeof返回的是整個陣列 的位元組數,乙個是 操作符返回 的是乙個指向陣列的指標 但不代表 兩者等價。int a 3 int b 宣告乙...