2016-03-03 110 views
-1

當我看到這這些行同樣的事情:指針和地址,該指針導致

BYTE MessageToProcess[MAX_MESSAGE_LENGTH]; 
TcpIpPacketHdr *pHdr = (TcpIpPacketHdr*)&MessageToProcess; 

我對自己說,第二行必須是這樣的:

TcpIpPacketHdr *pHdr = (TcpIpPacketHdr*)MessageToProcess; 

但是,當我在調試模式下檢查「pHdr」指向與兩個示例中的「MessageToProcess」相同的事物,而在第一個代碼中的MessageToProcess之前有一個「&」,所以通常pHdr應該包含MessageToProcess的地址,而不是它指向的字節,例如第一個messageToProcess中的元素。

所以這個問題發生了什麼?我們正在處理指向字節而不是函數的指針,所以添加&必須改變公式。

在我們使用PHDR這樣的代碼之後:

pHdr->size+2 

但在最初,第一個代碼,它包含指針保存的地址到陣列的第一個字節的地址。

+0

數組衰變爲指針。你會在任何書中找到關於該語言的解釋。 –

+0

和例如char **,指針類型的指針是不同於指針類型 – Aminos

+0

此代碼可能具有未定義的行爲,請檢查[嚴格別名規則](http://stackoverflow.com/questions/98650) /是什麼 - 是最嚴格走樣規則)。 – Lundin

回答

8

變量MessageToProcess是一個數組。它被放置在記憶中的某個地方。通過使用&MessageToProcess,我們得到存儲數組的那個地方的地址。 &MessageToProcess的類型是BYTE (*)[MAX_MESSAGE_LENGTH]

當您使用沒有地址運算符的MessageToProcess時,它會衰減到指向第一個元素的指針,即&MessageToProcess[0]。其類型是BYTE *

對於問題中顯示的示例,這兩個地址是相同的。當你試圖用這些指針來做更多的事情時,會產生不同。例如,如果你做(&MessageToProcess)[1]你會而不是得到與做MessageToProcess[1]時一樣的事情。


要有所顯現了,可以說我們有以下定義:

int a[4] = { 0, 1, 2, 3 }; 

然後,它是這樣的:

 
&a    &a+1 
|    | 
v    v 
+---+---+---+---+ 
| 0 | 1 | 2 | 3 | 
+---+---+---+---+ 
^ ^
| | 
a a+1 
+0

因此,如果MessageToProcess是動態數組BYTE * MessageToProcess = new BYTE [MAX_MESSAGE_LENGTH],則上面的第一個代碼應該是無效的:TcpIpPacketHdr * pHdr =(TcpIpPacketHdr *)&MessageToProcess;不再正確。我對嗎 ? – Aminos

+1

@Aminos這是正確的。如果'MessageToProcess'是一個指針變量,那麼'&MessageToProcess'就是指針變量的指針,即一個'BYTE **'。 –

+0

現在一切都很清楚。我很驚訝我仍然在C/C++中發現事物。我明白爲什麼像Java和Python這樣的新語言現在更受青睞。 – Aminos

3

MessageToProcess是一個數組。

在陣列的情況下,陣列的基址可以通過交替地按以下方式表示:

&MessageToProcess OR MessageToProcess OR &MessageToProcess[0]

+0

我認爲&MessageToProcess [0]與&MessageToProcess不同,但由於MessageToProcess不是BYTE *,所以它們是相同的。事實上,數組和指針之間存在差異 – Aminos