#include <cstdlib>
#include <iostream>
using namespace std;
void f(int k[0]){ --k[1]; }
void g(int *k){(*(--k))++;}
void h(int k[1]){--k;}
int main(){
int k[]={1,2,3,4};
f(k+2);
g(k+2);
h(k+2);
for (int i = 1; i < 4; i++)
cout << k[i];
}
正确的输出是333
,但我认为它是334
。
我不明白函数f在指令--k[1]
中究竟发生了什么。如果代码是k[0]--
,我可以同意正确的输出。有什么区别?
感谢
答案 0 :(得分:1)
--k[1]
递减k[1]
的值,给定f(k+2)
表示f()
- 本地k
指向来电者(即main()
's)k[2]
,并且1和2索引添加,你实际上是将调用者的k[3]
从4减少到3。
k[0]--
会在*k
处递减变量,f
在调用者的上下文中将k[2]
称为f
。
理解此代码的重要见解是:
所有功能g
,h
和int
最终都会获得指向k
的指针,他们的概念“k
”是完全独立于调用者的int
概念,特别是 - 它在调用者的k
数组中进一步偏移2 --k[1]
,
operator precedence:具体而言,在{{1}} 数组下标之后,应用前缀减量。
那就是说,paxdiablo肯定有一点......; - )。
答案 1 :(得分:1)
首先,所有三个函数都具有完全相同的签名。如果写完它会不那么令人困惑:
void f(int* pi){ --pi[1]; }
void g(int* pi){(*(--pi))++;}
void h(int* pi){--pi;}
(我已经更改了参数的名称以避免在下面的讨论中出现歧义。)
此外,当然:a[b]
根据定义为*(a + b)
,k
上的任何操作都会将其从int[4]
转换为int*
,指向第一个元素。
所以我们得到以下结果:
f( k + 2 );
// In f, pi is k + 2, so `pi[1]` is *(k + 3).
// After f, k = { 1, 2, 3, 3 }
g( k + 2 );
// In g, pi starts out as k + 2; it is then decrementd to give k + 1
// After g, k = { 1, 3, 3, 3 }
h( k + 2 );
// In h, pi is k + 2. A local copy of k + 2, so h doesn't change
// k at all.
结果是在{4}操作之后k
为{ 1, 3, 3, 3 }
。
答案 2 :(得分:1)
稍微更改代码,您可以查看每个步骤的操作:
#include <cstdlib>
#include <iostream>
using namespace std;
int *globk;
void dumpk(int *pk) {
cout << "Array:";
for (int i = 0; i < 4; i++)
cout << ' ' << globk[i];
cout << ", k at index " << (pk-globk) << '\n';
}
void f(int k[0]) { dumpk(k); --k[1]; dumpk(k); }
void g(int *k) { dumpk(k); (*(--k))++; dumpk(k); }
void h(int k[1]) { dumpk(k); --k; dumpk(k); }
int main(){
int k[]={1,2,3,4};
globk = k; // save for detecting where k is
f(k+2);
g(k+2);
h(k+2);
// slightly prettier output.
for (int i = 1; i < 4; i++)
cout << k[i] << ' ';
cout << '\n';
}
其输出显示了每个步骤的作用:
Array: 1 2 3 4, k at index 2
Array: 1 2 3 3, k at index 2
--k[1]; // -- array VALUE at INDEX 3 (2+1) down to 3
Array: 1 2 3 3, k at index 2
Array: 1 3 3 3, k at index 1
(*(--k))++; // -- POINTER to [1], then ++ that VALUE up to 3
Array: 1 3 3 3, k at index 2
Array: 1 3 3 3, k at index 1
--k; // Simply -- POINTER with no change to any VALUE
答案 3 :(得分:0)
此代码的作用是:
将从k[]
的第3个元素开始的数组传递给f
。 f
采用一维数组并减少其第二个元素(在这种情况下,它将为k[4]
,它将其值4更改为3)。
将k[]
中第3个元素的指针传递给g
。 g
获取一个指向整数或数组的指针,并首先减小指针的值(现在成为指向k[]
的第二个元素的指针),然后增加指向的值,从而改变指针的值2至3。
将从k[]
的第3个元素开始的数组传递给h
。 ``h接收一维数组并减少指向数组的指针(不是它指向的值),因此不会修改指向数组的值。
答案 4 :(得分:0)
f和g正在修改值,而h正在修改地址:
f(int k[0]){ --k[1]; }
f取一个参数,一个int数组;在这种情况下,k [1]与k ++相同;该函数递减位于下一个地址的元素的值与作为参数传递的元素的值。所以它在你的主体中递减了k [3]。
g是相对直接的,我认为你想出来了。
h类似于f
h(int k[1]){--k;}
h将一个int数组作为输入,并递减作为参数传递的地址。
希望这有帮助