簡體   English   中英

引用字符變量時,指針變量的地址存儲在哪里?

[英]Where is a pointer variable's address stored when referencing a character variable?

假設我們有一個這樣的字符指針:

static char *example[]={"doctor","who","hello"};

我對這種情況下發生的事情感到有些困惑。

  1. 指針example是否僅具有其自己的地址?

  2. 我在數組中擁有的字符串的每個存儲地址是否都與*example不同
    和彼此?

  3. 指針example是否只是引用了每個地址,並且還初始化了每個地址(如字符串聲明所示)?

我只使用C幾個月,所以我只是想抓住事物的本質,而且我聽說指針是C的最重要方面。

變量example是否僅具有其自己的地址?

是的,變量有其自己的地址。

我在數組中擁有的字符串是否每個都有一個與*example不同的內存地址?

是的,每個字符串都有自己的地址,彼此不同。 它也與變量example的地址不同。 但是,表達式*example與變量example並不相同。 見下。

指針示例是否只是引用了每個地址,並且還初始化了每個地址(如字符串聲明所示)?

可變example字符串數組引用在這個意義上的 example而不是它的地址)是數組的地址。

static char* example[] example聲明為指向char的指針的數組。 數組被初始化為三個字符串文字,因此example[0]"doctor"example[1]"who"example[2]"hello"

由於example是一個數組,因此數組標識符example將求值為數組第一個元素的地址。 如果您嘗試這樣的事情:

printf ("%p %p %p\n", example, &example, &example[0]);

您會看到它們都具有相同的值。 但是,所有這些在語義上都是不同的類型

example具有array of pointers to char的類型array of pointers to char

&example具有pointer to array of pointers to char的類型pointer to array of pointers to char

&example[0]的類型pointer to pointer to char

數組的每個元素都有其自己的地址。 嘗試這個:

printf ("%p %p %p\n", &example[0], &example[1], &example[2]);

第一個將與數組具有相同的地址,但是其他個將通過系統上指針的大小從該地址偏移(對於32位系統,通常為4個字節,對於64位系統,通常為8個字節)。

char ,在你的陣列中的每個指針example指向是第一char字符串文字的。 每個字符串文字都有自己的地址,可能在只讀內存段中。 您也可以嘗試以下方法:

printf ("%p %p\n", &example[0], example[0]); 

&example[0]是指向char的指針數組中的第一個指針的地址。

example[0]是指針數組中的第一個指針。 想想一個int數組。 該數組的每個元素都有一個地址和一個值,后者是一個int 由於example是一個指針數組,每個元件example都將有一個地址和一個值,后者是一個指針

您可以針對&example[1]等重復練習:

printf ("%p %p\n", &example[1], example[1]);
printf ("%p %p\n", &example[2], example[2]);

總結一下:

  1. 指向 char 的指針數組與其第一個元素具有相同的地址。
  2. 每個后續元素,即數組中的每個后續指針,都有其自己的地址。
  3. 這些指針中的每一個都指向一個字符串(字符串的第一個char ),該字符串具有自己的地址。

希望很清楚。

如果您聲明

char *example[] = {"doctor","who","hello"};

您將得到一個大小為3的數組,每個數組包含一個char *指針。 與...相同

char *example[3] = {"doctor","who","hello"};

但是,我們確實需要查看示例在代碼中如何聲明才能回答。

圖片可能會有所幫助。 以下內容並不代表任何特定的體系結構-所有地址值都是憑空提出的。


Item          Address            0x00  0x01  0x02  0x03
----          -------            ----  ----  ----  ----
              0x00004000          'd'   'o'   'c'   't'
              0x00004004          'o'   'r'  0x00   'w'
              0x00004008          'h'   'o'  0x00   'h'
              0x0000400c          'e'   'l'   'l'   'o'
              0x00004010         0x00    ??    ??    ??
...           ...                ...
example:      0x80001000         0x00  0x00  0x40  0x00
              0x80001004         0x00  0x00  0x40  0x07
              0x80001008         0x00  0x00  0x40  0x0b

字符串文字"doctor""who""hello"都以在程序的生命周期內分配的方式存儲(它們具有靜態存儲持續時間 ),並且可以以只讀方式存儲。數據段1

字符串文字"doctor"存儲在地址0x00004000"who"存儲在地址0x00004007"hello"存儲在地址0x0000400b

數組example借助static關鍵字也具有靜態存儲持續時間,但是實際上,它可能存儲在與字符串文字不同的存儲區域中。 數組從地址0x80001000開始,每個元素占用四個字節,因此&example[0] == 0x80001000&example[1] == 0x80001004&example[2] == 0x80001008

請注意,對於名為example的變量,它沒有單獨的存儲位置,該變量指向數組的第一個元素。 在C語言中,第一個元素的地址與數組本身的地址相同。 這很重要 ,並且是C語言最常被誤解的方面之一。 數組不是指針 ; 相反,在大多數情況下2 ,數組表達式將被轉換(“衰減”)為指針表達式,並且表達式的值將是第一個元素的地址。 如果您真的很感興趣,Dennis Ritchie在本文中概述了這種行為的原因。 向下滾動到“ Embryonic C”部分進行解釋。

example[0]存儲的值是字符串文字"doctor"的地址。 同樣, example[1]存儲字符串文字"who"的地址, example[3]存儲字符串文字"hello"的地址。


1.因此,嘗試修改字符串文字內容的行為未定義 -可能會按預期運行,可能崩潰或無法完全編譯。 不需要編譯器以任何特定方式處理這種情況,因此行為在不同的編譯器之間會有所不同。 您永遠不要嘗試修改字符串文字的內容。

2.此規則的例外情況是,數組表達式是sizeof的操作數或一元&運算符,或者是用於在聲明中初始化另一個數組的字符串文字。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM