我正在研究一个可以在链表上执行2个功能的小型测试程序:
所以我编写了两个可以执行此功能的函数。但它不起作用。
如果我调用函数append_work()
,它会打印出它附加了工作以及我传递的正确值。但是之后它似乎没有正确地将指针设置为下一个结构。我不知道为什么会这样。
当我调用get_work()
时,会发生类似的事情,它会正确打印当前的工作,但不会将其设置为下一个工作。 outptr只在那里,所以它返回要完成的工作的结构,而stil将work_travel设置为下一个!
我可能错过了一些非常明显的指针,但我没有看到它......
这是代码。它编译:
#define _POSIX_C_SOURCE 200809L
#define ERRNO_BUFSIZE 256
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <unistd.h>
int strerror_r(int errnum, char *buf, size_t buflen);
typedef struct work work;
struct work {
char *str;
int i;
work *next;
};
int append_work(work *ptr, char *work, int i) {
char strerror_buf[ERRNO_BUFSIZE];
ptr->next = malloc(sizeof(work));
if (ptr == NULL) {
strerror_r(errno, strerror_buf, ERRNO_BUFSIZE);
printf("malloc() err: %s\n",strerror_buf);
return -1;
}
ptr = ptr->next;
ptr->str=work;
ptr->i=i;
printf("appending work: %s\n",ptr->str);
ptr->next = NULL;
return 0;
}
int get_work(work *inptr, work *outptr) {
if (inptr == NULL) {
printf(" No work found...\n");
return -1;
} else {
outptr = inptr;
printf(" work found: str: %s|| int: %d\n",inptr->str, inptr->i);
inptr = inptr->next;
return 0;
}
}
int main() {
char strerror_buf[ERRNO_BUFSIZE];
work *root;
work *work_travel;
work *add_work;
work *curr_work;
root = malloc(sizeof(work));
if (root == NULL) {
strerror_r(errno, strerror_buf, ERRNO_BUFSIZE);
printf("malloc() err: %s\n",strerror_buf);
exit(1);
}
root->str="work 0";
root->i=0;
work_travel = root;
add_work = root;
append_work(add_work, "work 1", 1);
append_work(add_work, "work 2", 2);
append_work(add_work, "work 3", 3);
append_work(add_work, "work 4", 4);
append_work(add_work, "work 5", 5);
append_work(add_work, "work 6", 6);
append_work(add_work, "work 7", 7);
append_work(add_work, "work 8", 8);
append_work(add_work, "work 9", 9);
get_work(work_travel, curr_work);
get_work(work_travel, curr_work);
get_work(work_travel, curr_work);
exit(1);
}
答案 0 :(得分:1)
您永远不会返回列表中的新头,您在ptr
内更改了append_work()
,但add_work
中main()
的值未发生变化。
您应该返回新的列表头。
这是因为C严格call by value;参数是调用者上下文中相同值的副本,更改副本不会影响调用者的值。值的类型无关紧要,它始终是副本。
答案 1 :(得分:1)
首先,让&#34; struct work&#34;,一个名为&#34; work&#34;的类型,一个名为&#34;&#34;的工作&#34;是真的糟糕的编程风格。
也就是说,问题是inptr
是get_work
中的局部变量,当您调用work_travel
时,更改它不会更改get_work(work_travel, curr_work)
。你必须以某种方式返回更新的值,或者作为get_work的返回值(尽管使用此解决方案,你松开了成功标志,而不是你使用它:-)):
work *get_work (work *inptr, work *outptr) {
...
return inptr;
}
并称之为:
work_travel = get_work(work_travel, curr_travel);
或者传入一个指向待更新对象的指针,如:
int get_work (work **inptr_p, work *outptr) {
work *inptr = *inptr_p;
if (inptr == NULL) {
printf(" No work found...\n");
return -1;
} else {
outptr = inptr;
printf(" work found: str: %s|| int: %d\n",inptr->str, inptr->i);
inptr = inptr->next;
*inptr_p = inptr;
return 0;
}
}
...
get_work (&work_travel, curr_travel);