为什么我的void指针在程序中改变了值?

时间:2014-02-17 01:07:03

标签: c pointers malloc void

我在头文件中有以下内容。

struct SortedList
{
    void * data;         
    struct SortedList * next;       
    struct SortedList * previous;
    int (*compareFunc)(void *, void *);
    void (*destructor)(void *);
};
typedef struct SortedList* SortedListPtr;

SortedListPtr SLCreate(CompareFuncT cf, DestructFuncT df);

在.c文件中,我实现了SLCreate函数。

SortedListPtr SLCreate(CompareFuncT cf, DestructFuncT df)
{
    struct SortedList item;         
    item.data = malloc(100);
    item.data = NULL;           
    item.next = (struct SortedList *) malloc(sizeof(struct SortedList));
    item.previous = (struct SortedList *) malloc(sizeof(struct SortedList));
    item.compareFunc = cf;
    item.destructor = df;
    SortedListPtr ptr = (struct SortedList *) malloc(sizeof(struct SortedList));    
    ptr = &item;
    return ptr;
};

在main.c中,我尝试执行以下操作:     SortedListPtr list = SLCreate(& compareInts,& destroy);

//...... A bunch other code that does not alter list or it's contents at all. 



struct SortedList item = (*list);
void * data = item.data;

if (data != NULL)   
{
    printf("Why did data become not null???\n");
}

那么为什么数据不是null,因为我在SLCreate函数中指示它?我以为我使用了malloc,我该怎么做才能解决这个问题?

2 个答案:

答案 0 :(得分:1)

您将返回局部变量的地址,这是C中未定义的行为。

如果要返回一个指针,它指向的内存必须位于返回它的函数范围之外。因为要返回指向局部变量item的指针,所以当函数返回时,该内存位置不再可用。

我觉得你好坏参半了。你确实分配了内存,但没有错误地复制它。

SortedListPtr ptr = (struct SortedList *) malloc(sizeof(struct SortedList));    
ptr = &item;

在这里,您可以使用本地item的地址替换指针。相反,最后一行应该是:

*ptr = item;

以上内容会将item中存储的所有数据复制到ptr引用的内存位置。

还有一件事......我非常确定你不应该为previousnext分配内容。只需将它们设置为NULL即可。如果没有看到你打算如何使用它,我无法确定,但我可以看到你对指针感到困惑。这将更“正常”:

item.next = NULL;
item.previous = NULL;

答案 1 :(得分:0)

可能这种方式可以减少复制。因为我不确定你是否有复制结构

SortedListPtr SLCreate(CompareFuncT cf, DestructFuncT df)
{
    SortedListPtr ptr = (struct SortedList *) malloc(sizeof(struct SortedList));    

    ptr->data = malloc(100);
    ptr->data = NULL;           
    ptr->next = (struct SortedList *) malloc(sizeof(struct SortedList));
    ptr->previous = (struct SortedList *) malloc(sizeof(struct SortedList));
    ptr->compareFunc = cf;
    ptr->destructor = df;
    return ptr;
};