我有很多功能,如:
void write(char* param, int len)
{
//
}
我注意到我几乎从不使用&
运算符作为参数。当我传递数组时:
char in[20];
write(in, 20);
我不需要它,但是当我传递一个值时:
write(5, 1);
我似乎不需要它,当我传递指针时:
char* in = malloc(20);
write(in, 20);
我也不需要它。那么在什么情况下我真的需要打电话:
write(&in, 1);
因为我很困惑:D
答案 0 :(得分:4)
您确定第二种情况吗?它不能为我编译,应该是
char in = 5;
write(&in, 1);
答案 1 :(得分:2)
何时将值隐式转换为指针?
实际上,编译器可以隐式地将整数类型转换为指针。从理论上讲,这是非法的,接受它的编译器通常会发出警告:
example.c:2:6: warning: incompatible integer to pointer conversion initializing
'void *' with an expression of type 'int'
在上面的示例中:
char in = 5;
write(in, 20);
char
是一个整数类型,所以如果您的编译器允许它,可能被隐式转换为指针类型,尽管它不是C标准的一部分并且完全是编译器特异性。
请注意,标准允许使用强制转换将整数类型转换为指针类型,尽管结果是实现定义的:
char in = 5;
write((char *)in, 20);
唯一允许的隐式转换情况是整数常量0
,表示空指针:
write(0, 20); // allowed
请注意,整数常量本身是允许的,但值为0
的整数类型的变量不是:
char in = 0;
write(in, 20); // not allowed
至于其他人,当你传递一个指针时,你显然不需要&
,因为它已经是一个指针。 When you pass an array, it decays to a pointer所以你也不需要&
。在这两种情况下,使用它实际上都是非法的,因为上面的函数需要char *
并分别使用char **
和char (*)[20]
。
答案 2 :(得分:1)
如果以某种方式将函数'write'的原型复制到调用此函数的文件中,如下所示。
void write(char *in, int len);
void foo(int bar){
char in=5;
write(in, 1);
}
您可能会收到警告。因为in不是指针,尽管5可以是地址。 我想如果您的程序已成功编译和链接,它将在运行时崩溃。
答案 3 :(得分:1)
使用;
return_type function_name(prim_data_type* param...)
param是一个指向内存中地址的指针,*param
是该地址中的值。
答案是关于你想对这个param
做什么。
char in[20];
说“ in ”是第一个元素的地址。所以在函数调用:
write(in, 20);
您要发送第一个元素的地址,因此在函数实现中,您可以通过*param
访问第一个元素,使用*(param+1)
或param[1]
访问第二个元素等。
你感到困惑的地方是:
char in = 5;
write(in, 1);
因为在中是地址5(00000005),所以在执行该功能时,您将访问该位置,无论哪个值。你必须小心这样使用。
在malloc操作中:
char* in = malloc(20);
write(in, 20);
in
是一个指向地址的指针(第一个元素的地址),占用20个char元素可以占用空间。在函数中,您可以使用param指针访问所有元素(*param
是第一个元素,*(param+7)
或param[7]
是8.元素)
在结论中,当你想在另一个函数中使用主数据类型变量(int,float,char ..)时,你必须使用;
write(&in);
通过这样做,在写函数的实现中,您可以访问该变量,将值更改为*param
而不会产生混淆。
注意:为了更好地理解,这里简化了一些解释。这里将欢迎额外的警告。
答案 4 :(得分:0)
函数和数组在某些上下文中会衰减为指针。函数可以衰减为指向函数的指针,数组可以衰减成指向数组第一个元素的指针。没有其他类型的行为。
这个例子:
char in = 5;
write(in, 1);
虽然错了。在这种情况下,你肯定需要&
。你确定它的效果如此吗?