char *name 與 char name的區別(基礎知識) 在
學習過程中發現了乙個以前一直預設的錯誤,同樣char *c = "abc"和char c="abc",前者改變其內容程式是會崩潰的,而後者完全正確。
程式演示:
測試環境devc++
**
<
string.h>
執行結果
2293628 4199056 abc
2293624 2293624 abc
2293620 4199056 abc
參考資料:
首先要搞清楚編譯程式占用的記憶體的分割槽形式:
一、預備知識—程式的記憶體分配
乙個由c/c++編譯的程式占用的記憶體分為以下幾個部分
1、棧區(stack)—由編譯器自動分配釋放,存放函式的引數值,區域性變數的值等。其操作方式類似於資料結構中的棧。
2、堆區(heap)—一般由程式設計師分配釋放,若程式設計師不釋放,程式結束時可能由os**。注意它與資料結構中的堆是兩回事,分配方式倒是類似於鍊錶,呵呵。
3、全域性區(靜態區)(static)—全域性變數和靜態變數的儲存是放在一塊的,初始化的全域性變數和靜態變數在一塊區域,未初始化的全域性變數和未初始化的靜態變數在相鄰的另一塊區域。程式結束後由系統釋放。
4、文字常量區—常量字串就是放在這裡的。程式結束後由系統釋放。
5、程式**區
這是乙個前輩寫的,非常詳細
<
string.h>
int a=0;
//全域性初始化區
char *p1;
//全域性未初始化區
main()
對應的彙編**
10:a=c[1];
004010678a4df1movcl,byteptr[ebp-0fh]
0040106a884dfcmovbyteptr[ebp-4],cl
11:a=p[1];
0040106d8b55ecmovedx,dwordptr[ebp-14h]
004010708a4201moval,byteptr[edx+1]
004010738845fcmovbyteptr[ebp-4],al
第一種在讀取時直接就把字串中的元素讀到暫存器cl中,而第二種則要先把指標值讀到edx中,在根據edx讀取字元,顯然慢了。
2.7小結:
堆和棧的區別可以用如下的比喻來看出:
使用棧就象我們去飯館裡吃飯,只管點菜(發出申請)、付錢、和吃(使用),吃飽了就走,不必理會切菜、洗菜等準備工作和洗碗、刷鍋等掃尾工作,他的好處是快捷,但是自由度小。
使用堆就象是自己動手做喜歡吃的菜餚,比較麻煩,但是比較符合自己的口味,而且自由度大。
總結:1. char *c1 = "abc";
2. char c2 = "abcd";
3. char *c3 = ( char* )malloc(4);
4. c3 = "abc"
5. strcpy(c3,"1234");
6. c3[0] = 'g';
分析:
1。上面**中的 字串常量 "abc","abcd","1234",都是存放在所謂的文字常量區;
2。c1,c2,c3 這個三變數,都存放在棧中
3。在vc中測試,cpu4個位元組對齊吧,ebp為棧頂指標
c1 的位址,就是ebp - 04h,占用4個位元組
c2 的位址,就是ebp - 0ch,占用8個位元組
c3 的位址,就是ebp - 10h,占用4個位元組
4。儲存內容比較
c1 的4個位元組,儲存是的字串常量 "abc"的位址
c2 的8個位元組,儲存就是就"abcd\0"還有3個位元組未用;它不儲存字串常量 "abcd"的位址,而是將內容複製過來
c3和c1一樣,也是儲存乙個位址,但這個位址,是在堆中,
結論:
所謂c中char * 和 char 的區別
char * 在棧中是4個位元組的指標,
而 char 將在棧中申請合適的記憶體來儲存初始化的資料,
也就是說
char c2="abcd"; 和char c2[5]="abcd";一樣的;
若char c2[n],則在棧中分配n個位元組;
所以c2[1]='0'是正確的,c1[1]='a'是錯誤的,因為字串常量不允許修改;
同時也說明了上面的**
...
char a=1;
char c="1234567890";
char *p="1234567890";
a = c[1];
a = p[1];
...
a = c[1];要比a = p[1];快的原因,少了一條指令嘛
和 區別和聯絡, 和 區別和聯絡
和 區別和聯絡,和 區別和聯絡,實際專案中,什麼情況用哪種?首先,和 的聯絡 共同點 和 都可以用作 邏輯與 運算子,都是雙目運算子。具體要看使用時的具體條件來決定。無論使用哪種運算子,對最終的運算結果都沒有影響。情況1 當上述的運算元是boolean型別變數時,和 都可以用作邏輯與運算子。情況2 ...
rpx和樣式和class和flex
5 style 靜態的樣式統一寫到 class 中。style 接收動態的樣式,在執行時會進行解析,請盡量避免將靜態的樣式寫進 style 中,以免影響渲染速度。例 6 class 用於指定樣式規則,其屬性值是樣式規則中類選擇器名 樣式類名 的集合,樣式類名不需要帶上.樣式類名之間用空格分隔。關於f...
if和switch和for語句
if和switch很像。具體什麼場景下,應用那個語句呢?如果判斷的具體數值不多,而是符合byte,short,int,char,字串。這五種型別。雖然兩個語句都可以使用,建議使用switch語句,因為效率稍高。其他情況,對區間判斷,對結果為boolean型別判斷,使用if,if的使用範圍更廣。whi...