[英]C function return statement
目前正在使用第二版K&R书籍学习C。 我对这个示例以及如何将行变量的值从getlines
函数更改为字符串感到困惑。
int main()
{
char line[MAXLINE];
int found = 0;
while (getlines(line, MAXLINE))
printf("Test: %s\n", line);
}
int getlines(char s[], int lim)
{
int c, i;
i = 0;
while (--lim > 0 && (c=getchar()) != EOF && c != '\n')
s[i++] = c;
if (c == '\n')
s[i++] = c;
s[i] = '\0';
return i;
}
程序输出“ Test:[来自getlines的字符串]”。 如果我从未从getlines
的返回值中分配“ char line”到getlines
返回一个int
的事实, getlines
“ line”的值如何分配给我输入到变量“ s”中的字符串?
您显然假设函数getlines()
返回字符串。 它不是。
它返回读入该行的字符数。 main中的line[]
变量作为参数传递给getlines ,该方法将该参数作为变量s[]
。 注意它是如何给s[i++]
分配字符s[i++]
。
当您将line
作为参数传递时, getline()
填充它。 返回的int
是执行后函数的状态。
在C函数调用中,所有参数都由value传递,因此该函数具有它们的副本。 因此,函数永远不可能更改参数。 听起来似乎与您在此处观察到的情况相矛盾,但事实并非如此:
C语言中的数组有些特殊。 数组标识符几乎在任何地方( 数组 sizeof
除外)都会被评估为数组第一个元素 (也称为指针)的地址 。 不可能分配一个数组,也不可能传递一个数组(作为函数参数或返回值)。
同样,这看起来是矛盾的,但是函数声明还有另一条规则:如果函数声明包含数组类型 ,则会自动将其调整为相应的指针类型 。 所以你的功能
int getlines(char s[], int lim);
实际上是以下功能:*)
int getlines(char *s, int lim);
调整函数声明中的类型以及将数组的标识符作为指针评估在一起的效果通常表示为数组作为指针的衰减 。 真正传递给函数的是指针,而不是数组。 索引该指针后,函数中的代码将访问原始数组。 指针当然是按值传递的 ,您的函数不会更改此指针,但可以更改它指向的指针。
*)风格注释:我更喜欢始终使用指针类型编写函数声明,因为无论如何这都是编译器所看到的,因此避免了混淆。 当然,有人认为写数组类型是件好事,因为它记录了该函数应该传递给数组的指针的意图 。
如果我从未将“字符行”分配给getlines的返回值
正确,您永远不要将getlines
的返回值分配给variable line
。
“ line”的值如何分配给我输入到变量“ s”中的字符串
当您执行getlines(line, MAXLINE)
,变量line
尽管声明为数组,但在传递时会衰减到指向数组第一个元素的指针。 然后,在getlines
中执行s[i++] = c;
,您实际上是在写传递给getlines
的地址(或离开该地址的跳数)。 请记住,索引数组s[i++]
会隐式取消对i
引用,使其跳离s
包含的地址。 然后,当您在main
功能中打印line
,您会发现一些信息已放置在数组中。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.