int check_authentication(char *password)
// 1
{
int auth_flag = 0;
char password_buffer[16];
strcpy(password_buffer, password); // 2
if(strcmp(password_buffer, "brillig") == 0)
auth_flag = 1;
if(strcmp(password_buffer, "outgrabe") == 0)
auth_flag = 1;
return auth_flag;
}
check_authentication(argv[1]) // Passing a 'Command Line argument'
// ( which is a string in this example) to the check_authentication function.
我有两个问题。上面标有1和2的行,
该函数需要一个字符指针作为参数。但是我们传递一个"字符串"我,一个字符数组作为参数。怎么?????
指针所占据的地址"密码" (指向一个字符)被复制到" password_buffer"阵列。对我来说完全是无稽之谈 。请解释一下。
答案 0 :(得分:5)
您正在传递一个指向字符串中第一个字符的字符指针。你实际上并没有传递整个字符串。
strcpy
函数读取此指针指向的字符,然后继续读取下一个内存位置的连续字符,直到遇到空终止符。
strcpy
的第一个参数以及strcmp
的两个参数都以相同的方式工作。
答案 1 :(得分:2)
该函数需要一个字符指针作为参数。但是我们传递一个"字符串"我,一个字符数组作为参数。怎么?????
除非它是sizeof
或一元&
运算符的操作数,或者是用于在声明中初始化另一个数组的字符串文字,表达式为类型" T
"的N元素数组;将被转换("衰减")到类型为&#34的表达式;指向T
"的指针,并且表达式的值将是第一个元素的地址。阵列。
致电时
strcpy(password_buffer, password);
表达式password_buffer
具有类型" 16个元素的数组char
&#34 ;;由于表达式不是sizeof
或一元&
运算符的操作数,因此表达式被转换("衰减")到#34;类型指针char
",表达式的值是第一个元素的地址。此指针值是传递给strcpy
的值。
简而言之,只要将数组表达式传递给函数,函数就会收到指针值。在函数参数声明的上下文中,T a[]
和T a[N]
将被解释为T *a
。
相信它或者不,Ritchie确实有理由以这种方式设计语言;有关详细信息,请参阅this paper(查找标题为" Embryonic C")的部分。
指针所包含的地址"密码" (指向一个字符)被复制到" password_buffer"阵列。对我来说完全是无稽之谈 。请解释一下。
那不是发生了什么;发生了什么strcpy
正在从password
给password_buffer
的地址开始复制缓冲区的内容。想象一下以下内存映射:
Item Address 0x00 0x01 0x02 0x03
---- ------- ---- ---- ---- ----
"foo" 0x7fffc7cf4b22 'f' 'o' 'o' 0
argv[1] 0x7fffc7cf2670 0x00 0x00 0x7f 0xff
0xc7 0xcf 0x4b 0x22
password 0x7ffffdbe1878 0x00 0x00 0x7f 0xff
0xfd 0xbe 0x2v 0x22
password_buffer 0x7ffffdbe1880 0x?? 0x?? 0x?? 0x??
0x?? 0x?? 0x?? 0x??
0x?? 0x?? 0x?? 0x??
0x?? 0x?? 0x?? 0x??
其中0x??
表示未知/不确定的字节值。
命令行参数字符串" foo"存储在地址0x7fffc7cf4b22
。请注意,在C中,字符串只是一个由0值字节终止的字符值序列。字符串存储为char
({+ 1}}在C ++中的数组),但并非所有const char
数组都包含字符串。
char
表达式求值为第一个命令行参数的地址,该地址是字符串argv[1]
的地址,即"foo"
。此值将传递给0x7fffc7cf4b22
函数,并存储到check_authentication
参数中。请注意,password
和argv[1]
是内存中的不同项(它们具有不同的地址),但两者都包含相同的值(字符串password
的地址) 。
"foo"
数组从地址password_buffer
开始。由于它没有声明0x7ffffdbe1880
并且没有显式初始值设定项,因此数组的内容是 indeterminate 。
static
函数将从地址strcpy
开始的字符串内容复制到从地址0x7fffc7cf4b22
开始的缓冲区,直到它看到0值字节。在致电0x7ffffdbe1880
之后,我们的记忆如下:
strcpy
答案 2 :(得分:1)
字符串实际上只是以空字节\0
结尾的字符数组。数组是字符串本身,但char指针是数组第0个位置的内存位置。
strcpy
读取从char指针指向的内存位置开始的字符,直到遇到空终止字符。
答案 3 :(得分:1)
数组实际上并没有这样传递。传递的是指向数组第一个元素的指针。 C中的字符串实际上是一个带有终止NUL
的字符数组,它是指向其传递的第一个元素的指针。
您真的应该仔细阅读strcpy
联机帮助页http://linux.die.net/man/3/strcpy。没有地址被复制到那里。所有函数都是将一个字符串(一个字符数组)password
指针指向并将所有在该地址找到的字符复制到NUL
到password_buffer
指针所指向的地址