gpt4 book ai didi

c - 为什么在此 K&R 示例中函数传递指针是有效的?

转载 作者:行者123 更新时间:2023-12-01 15:08:34 24 4
gpt4 key购买 nike

我正在通过阅读 K&R(ANSI 版) 学习 C,辅以 21st Century C。我会说我已经对指针的大部分基础知识非常有信心。这意味着我知道您必须非常小心地从一个函数中传递指针,这些指针既不是首先传递给它的,也不是 malloced 的。所以这个例子让我难住了。它来自 §5.6,第 109 页:

#define MAXLEN 1000 /* max length of any input line */
int getline(char *, int);
char *alloc(int);

/* readlines: readinputlines */
int readlines(char *lineptr[], int maxlines)
{
int len, nlines;
char *p, line[MAXLEN];

nlines = 0;
while ((len = getline(line, MAXLEN)) > 0)
if (nlines >= maxlines || (p = alloc(len)) == NULL)
return -1;
else {
line[len-1]='\0'; /* delete newline */
strcpy(p, line);
lineptr[nlines++] = p;
}
return nlines;
}

strcpy() 之前定义为:

/* strcpy: copy t to s; pointer version 3 */
void strcpy(char *s, char *t)
{
while (*s++ = *t++)
;
}

我不明白 p 指向的内存如何在函数返回后保留在范围内。这就是我的理解。指针 p 在函数内声明 - 因此它在自动内存中。至于它指向什么,它没有明确分配任何内存。然后当 strcpy 被调用时,值从 line 复制到 p 指向的任何地方。

我还谈到了 21 世纪 C 中讨论指针危险的观点,并举例说明试图将在自动内存中声明的数组从函数中传递出去肯定是不行的。 (第 109 页:“指向已自动释放的内存块的指针比无用更糟糕。”)所以我能理解上述代码有效的唯一方法是通过声明 p不是作为在自动内存中显式分配内存块的数组,而是作为指针,它的内存分配以某种方式隐式处理。那是对的吗?内存分配是如何工作的?

注意:通过阅读21st Century C,我试图抵消K&R 可能给我带来的任何不良做法。我知道这不是最好的标准,而且我可能永远不会按照本例中演示的方式编写代码。但我还是想了解一下。

最佳答案

确实,指针p 本身驻留在自动内存中。但是,在评估以下 if 语句的条件期间,它会被分配一个内存块:

if (nlines >= maxlines || (p = alloc(len)) == NULL)

更具体地说,如果条件的第一项为假(因为 or 逻辑运算符是短路运算符),则计算第二项,执行内存分配并检查是否成功。

根据我对 K&R 的旧知识,alloc 函数是 malloc 的简化版本,在您到达此示例之前的某处定义。但是,内存分配函数(例如标准的 malloc,此处以 alloc 为例)的要点是允许您在堆上保留内存。堆是在程序执行期间定义的内存区域,它不会自动管理,即编译器不会对其进行任何操作,除非您明确告诉它这样做。因此,您可以按值返回/传递指针 p。变量本身的内存没有多大用处;它的值(value)才是最重要的。它指向一个已分配的内存区域,只要你愿意,它就会一直留在那里(直到你明确释放它)。只需确保在释放该区域之前不会丢失该区域的内存地址即可。

关于c - 为什么在此 K&R 示例中函数传递指针是有效的?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48646411/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com