Почему этот malloc не работает в C? - PullRequest
0 голосов
/ 26 октября 2010

Просто пытаюсь создать своего рода хеш-таблицу, в которой каждый узел является связанным списком.

Возникли проблемы при инициализации пространства, что я делаю неправильно?

#include <stdlib.h>

typedef struct entry {
 struct entry *next;
 void *theData;
} Entry;


typedef struct HashTable {
 Entry **table;
 int size;
} HashTable;

int main(){
 HashTable *ml;
 ml = initialize();
 return 0;
}

HashTable *initialize(void)
{
 HashTable *p;
 Entry **b;
 int i;


 if ((p = (HashTable *)malloc(sizeof(HashTable *))) == NULL)
  return NULL;
 p->size = 101;

 if ((b = (Entry **)malloc(p->size * sizeof(Entry **))) == NULL)
         return NULL;

 p->table = b;

 for(i = 0; i < p->size; i++) {
  Entry * b =  p->table[i];
  b->theData = NULL;
  b->next = NULL;
     }

 return p;
}

Ответы [ 4 ]

9 голосов
/ 26 октября 2010

Вам нужно изменить sizeof(HashTable*) на sizeof(HashTable) и аналогично sizeof(Entry **) на sizeof(Entry *) И второе: для каждого Entry вам нужно выделить память, снова используя malloc внутри цикла.

1 голос
/ 26 октября 2010
 if ((p = malloc(sizeof(HashTable))) == NULL) 
  return NULL; 
 p->size = 101;  

 if ((b = malloc(p->size * sizeof(Entry *))) == NULL) 
         return NULL; 

Я считаю, что удаление результатов приведения malloc() является наилучшей практикой.

Плюс, поскольку @Naveen был первым, кто указал, что вам также необходимо выделить память для каждого Entry.

0 голосов
/ 26 октября 2010

Кроме того, вы можете статически объявить вашу HashTable, либо локально, либо в некотором регионе, достаточно высоком в стеке, что стек не является восходящим (в памяти), пока он используется, и передать указатель на HashTable вашей функции инициализациичтобы избежать malloc.malloc работает медленно.

Итак, в основном вы можете сделать:

HashTable table;InitializeHashTable (& table);

// использовать таблицу (не нужно освобождать) // просто не возвращать таблицу

0 голосов
/ 26 октября 2010

Во-первых, ваши sizeofs неверны. T * = malloc (num * sizeof (T)) является правильным. Вы также можете использовать calloc.

Вы повторно используете b для разных целей, так что это довольно запутанно. Не очень хорошо, если использовать односимвольную переменную.

p-> таблица, которая была b выделена, но не инициализирована, то есть она не указывает на что-либо полезное, тогда вы пытаетесь разыменовать ее.

Вам нужно сначала заполнить указатели Entry *, и они должны указывать на действительные структуры Entry, если вы собираетесь разыменовать их.

Ваш процесс, вероятно, умирает в строке b> theData = NULL

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...