[英]C pointers in functions
在我的c應用程序中,我有以下聲明:
typedef double mat[MAX_SIZE][MAX_SIZE];
我還有一個全局變量:
mat aaa;
在函數中,我想執行以下操作:
void func2(mat ccc)
{
ccc = aaa;
}
void func1()
{
mat bbb;
func2(bbb);
bbb[1][2] = 3;
}
我希望在func2()
之后對bbb
進行的操作會影響全局變量aaa
,但它們不會。
關於為什么這種行為不是我期望的任何建議?
您需要使bbb
成為指針並發送bbb
的地址。
void func1()
{
mat *bbb;
func2(&bbb);
(*bbb)[1][2] = 3;
}
然后像這樣編輯func2
:
void func2(mat **ccc){
*ccc=&aaa;
}
您的類型mat
不是指針類型,而是數組。 您不能在C中為數組變量賦值。解決問題的常用方法是使用指針:
void func1(void)
{
mat *bbb = &aaa;
(*bbb)[1][2] = 3;
}
您的意思是bbb[1][2] = 3;
會在aaa
上完成嗎? 然后,您必須這樣做:
mat aaa;
mat* func2() {
return &aaa;
}
void func1() {
mat* bbb = func2();
(*bbb)[1][2] = 3;
}
這段代碼中存在概念錯誤-數組表達式可能不是賦值的目標。 如果你想寫
void func1(void)
{
mat bbb;
bbb = aaa;
bbb[1][2] = 3;
}
編譯器將對表達式bbb = aaa
進行診斷(gcc給出了“分配中的不兼容類型”診斷信息,因為aaa
轉換為指針類型;更多內容請參見下文)。 通過將bbb
傳遞給func2
來嘗試執行的操作實際上是同一件事,並且最終將不起作用。
讓我們擺脫typedef,以便我們可以看到實際的類型
double aaa[MAX_SIZE][MAX_SIZE];
...
void func2(double (*ccc)[MAX_SIZE])
{
ccc = aaa;
}
void func1()
{
double bbb[MAX_SIZE][MAX_SIZE];
func2(bbb);
bbb[1][2] = 3;
}
除非它是sizeof
的操作數或一元&
運算符,或者是用於在聲明中初始化另一個數組的字符串文字,否則“ N的T
元素數組”類型的表達式將被“指針”類型的表達式替換到T
“,其值為數組的第一個元素的地址。 當你調用func2
,表達bbb
從類型“轉換MAX_SIZE
的陣列MAX_SIZE
的陣列double
”到“指針MAX_SIZE
的陣列double
”; 因此,將ccc
聲明為double (*ccc)[MAX_SIZE]
。
類似地,在func2
ccc = aaa
中,表達式aaa
從double [MAX_SIZE][MAX_SIZE]
類型轉換為double (*)[MAX_SIZE]
。
到目前為止, func2
是潔凈的,因為ccc
是指針表達式,而不是數組表達式,因此允許分配。 ccc
也恰好是與bbb
完全不同的實體(它接收bbb
求值的指針值的副本),因此寫入ccc
對bbb
沒有影響。 如果您嘗試通過傳遞指向bbb
的指針來解決該問題,則如下所示:
void func2(double (*ccc)[MAX_SIZE][MAX_SIZE])
{
*ccc = aaa;
}
void func1(void)
{
double bbb[MAX_SIZE][MAX_SIZE];
func2(&bbb);
bbb[1][2] = 3;
}
編譯器將對*ccc = aaa
拋出診斷,這可能是因為*ccc
具有數組類型,或者是因為*ccc
和aaa
的類型不兼容(請記住, aaa
被轉換為指針表達式)。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.