它显示了我的主函数在HTSize时对大小8的无效读取,对于空散列,它似乎可以工作(它打印0),但我认为问题是,HTCreate中的初始化散列作为HTSize中的参数传递,但已单元化。
我试过(不在显示的代码中)将参数作为定义为HTSize(HThash**)的&Table传递,但程序没有运行,valgrind也显示“地址0x0不是stack'd、malloc'd或(最近)free'd”。在函数内部,我还将一个指针T放在散列上,以取消对**散列的引用。我在linux中工作。

typedef char* KeyType;
typedef int HTItem;
typedef struct node{
    KeyType key;
    HTItem item;
    struct node *next;
}List;
typedef struct {
    List *head;
}TableEntry;
typedef TableEntry *HTHash;

HTHash* HTCreate(void);
int HTSize(HTHash);

int TABLESIZE = 10;

int main(void)
{
    HTItem *p;
    HTHash *Table = HTCreate();
    printf("%d\n",HTSize(*Table));
}

HTHash* HTCreate(void)
{
    int i;
    HTHash table = (HTHash)malloc(TABLESIZE*sizeof(TableEntry));
    HTHash *T;
    for(i=0;i<TABLESIZE;i++)
        table[i].head = NULL;
    T = &table;
    return T;
}

int HTSize(HTHash hash)
{
    int i,count=0;
    List *temp = (List*)malloc(sizeof(List));
    for(i=0;i<TABLESIZE;i++)
    {
        if(hash[i].head != NULL)
        {
            count++;
            temp = hash[i].head->next;
            while(temp != NULL)
            {
                count++;
                temp = temp->next;
            }
        }
    }
    return count;
}

错误可能在HTCreate中,但我不确定。我检查了hash是否在主函数中初始化,它确实初始化了。

最佳答案

您的问题在HTCreate函数中有效:它返回&table函数的本地值。
演示

HTHash *HTCreate(void)
{
    int i;

    HTHash table = NULL;

    printf("&table before malloc: %p\n", &table);

    table = malloc(TABLESIZE*sizeof(TableEntry));

    printf("&table after  malloc: %p\n", &table);

    HTHash *T;

    for(i=0;i<TABLESIZE;i++)
        table[i].head = NULL;

    T = &table;
    return T;
}

将打印:
&table before malloc: 0x7fff200eb818
&table after  malloc: 0x7fff200eb818

我们看到malloc对这个值没有影响。
由于这是函数的本地操作,在另一个函数中使用它可能会导致任何事情(未定义的行为)
从函数返回所需内容的好方法是返回HTHash类型:
HTHash HTCreate(void)
{
    int i;

    HTHash table = malloc(TABLESIZE*sizeof(TableEntry));

    for(i=0;i<TABLESIZE;i++)
        table[i].head = NULL;

    return table;
}

看看里面做了什么,我发现这个函数可以简化:
HTHash HTCreate(void)
{
    return calloc(TABLESIZE, sizeof(TableEntry));
}

07-26 06:04