【问题标题】:Calling a function with a pointer does not change value of that pointer? [duplicate]用指针调用函数不会改变该指针的值? [复制]
【发布时间】:2020-01-14 20:30:45
【问题描述】:

当我调用“InitAnimation”函数时,我传递了我的对象 RG 的地址。当我分配该对象的“animationName”字段时,我可以成功打印该字段。 但是当我返回 main 并调用函数“ReportAnimation”时,我无法打印该值并且我的程序崩溃了? 为什么当我分配了该 objects 字段时,它并没有全局更改,而是仅在本地函数中更改?

我也尝试为 animationName 字段分配内存,但这不起作用。

struct Frame {
    char* frameName;
    struct Frame* pNext;
};

typedef struct {
    char* animationName;
    struct Frame* frames;
}Animation;


int main(void) {

    char response;

    BOOL RUNNING = TRUE;

    Animation RG;

    InitAnimation(&RG);

    while (RUNNING) {
        printf("MENU\n Enter 1 to ReportAnimation\n");
        scanf("%c", &response);

        switch (response) {
        case '1':InsertFrame(&RG); 
        break;
    }
    }

    return 0;
}

void InitAnimation(Animation* pointer) {

    pointer = (Animation*)malloc(sizeof(Animation));

    char* input;
    input = (char*)malloc(sizeof(input));

    printf("Please enter the Animation name:");
    fgets(input, 32, stdin);

    //pointer->animationName = (char*)malloc(sizeof(char)*10);

    //Setting animation name
    pointer->animationName = input;


    //This print function works
    printf("\nThe name is %s", pointer->animationName);

}

void ReportAnimation(Animation* pointer) {

    //This print function does not work
    printf("Animation name is %s\n", pointer->animationName);

}

我希望 initAnimation 函数改变 Animation 结构的字段 我希望 reportAnimation 函数打印出该字段,证明它已更改

【问题讨论】:

  • InitAnimation 中,pointer 已经指向来自调用者的Animation 变量,因此pointer = malloc(sizeof(Animation)); 是多余的、错误的,并且存在内存泄漏。此外,input = malloc(sizeof(input)); 将分配一个指针大小的内存块(可能是 4 或 8 个字节长),这可能不是您想要的大小,因为您将大小 32 传递给了fgets

标签: c pointers struct malloc function-pointers


【解决方案1】:

改变函数变量的值(包括那些声明为参数的)对调用者没有影响。

void bad1(int i) {
   i = 1;  // No effect on the caller.
}

void bad2(void* p) {
   p = NULL;  // No effect on the caller.
}

如果你想改变调用者中的一个变量,你需要传递一个指向它的指针。

void good1(int* i_ptr) {
   *i_ptr = 1;
}

void good2(void** p_ptr) {
   *p_ptr = NULL;
}

所以要么将一个指针传递给一个指针,要么将一个指针传递给一个已经分配的结构。你可以使用

Animation ani;
Animation_init(&ani, name);
...
Frame* frame = Frame_new(name);
Animation_append_frame(&ani, frame);
...
Animation_destroy(&ani);

Animation* ani = Animation_new(name);
...
Frame* frame = Frame_new(name);
Animation_append_frame(ani, frame);
...
Animation_delete(ani);

假设你有

typedef struct Frame {
    char* name;
    struct Frame* next;
} Frame;

typedef struct {
    char* name;
    Frame* first_frame;
    Frame* last_frame;
} Animation;

void Animation_init(Animation* self, const char* name) {
    self->name = strdup(name);
    self->first_frame = NULL;
    self->last_frame = NULL;
}

void Animation_destroy(Animation* self) {
    Frame* head = self->first_frame;
    while (head != NULL) {
       Frame* next = head->next;
       Frame_delete(head);
       head = next;
    }

    free(self->name);
}

Animation* Animation_new(const char* name) {
    Animation* self = malloc(sizeof(Animation));
    Animation_init(self, name);
    return self;
}

void Animation_delete(Animation* self) {
    Animation_destroy(self);
    free(self);
}

void Animation_append_frame(Animation* self, Frame* frame) {
   if (self->last_frame == NULL) {
      self->first_frame = frame;
   } else {
      self->last_frame->next = frame;
   }

   while (frame->next != NULL)
      frame = frame->next;

   self->last_frame = frame;
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-12-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多