динамичен масив с указатели за структуриране на възли

Имам проблем с някакъв код на C и наистина ще имам нужда от вашата помощ. Ами имам тези 2 структури (от тях се иска да бъдат така, така че не можем да ги променим)

struct node{
    struct list_node **table;
    int table_size;
};

struct list_node{
    int num;
    struct list_node *ptr;
};

и както можете да видите в първия имаме масив с указатели във възлите на нашия списък. в main създаваме необходимото пространство в паметта, за да започнем по този начин

struct node *nodeT;
struct list_node *root, *curr, **temp;

root = (struct list_node*)malloc(sizeof(struct list_node));       // root node of list

nodeT = (struct node*)malloc(sizeof(struct node));                // single node
nodeT->table = (struct list_node**)malloc(sizeof(struct list_node*)); 
nodeT->table_size = 0;

и след това създавам списъка

for(i=0 ; i<X ; i++){     // X is important for the errors and i'll explain why
  curr = (struct list_node*)malloc(sizeof(struct list_node));
  curr -> num = (i+1);
  curr -> ptr = root;
  root = curr;
}

сега минавам през списъка и разширявам масива в първата структура за всеки възел от списък, който намеря, за да въведа указател към правилния възел.

for(curr=root ; curr!=NULL ; curr=curr->ptr){               

  nodeT->table[nodeT->table_size] = curr;
  nodeT->table_size++;

  temp = (struct list_node**)realloc(nodeT->table , nodeT->table_size*sizeof(struct list_node *));
  if(temp!=NULL)
      nodeT->table = temp;
  else{
     printf("Memory error\n");
    return 1;
  }
}

използвам тази структура list_node **temp, за да запазя безопасен nodeT и след проверка, ако всичко е наред, поставям отново temp в nodeT, в противен случай спирам програмата. В крайна сметка отпечатвам съдържанието на списъка чрез указателите на масив като този

for(i=0 ; i<nodeT->table_size ; i++)
   printf("-> %d ", nodeT->table[i]->num);
printf("\n");

и излизам от програмата. парадоксът в това е, че за X 1-4 всичко работи добре, но за 5+ има проблем и получавам съобщение

" ** glibc открит * ./dynamix_table_realloc: realloc(): невалиден следващ размер: 0x0000000000819050 * "

и още около 20 реда, които наистина не ми помагат. Надявам се, че ще го направите и затова публикувах това. Благодаря предварително!


person user3162585    schedule 05.01.2014    source източник


Отговори (1)


Не сте разпределили достатъчно памет тук:

temp = (struct list_node**)realloc(nodeT->table , nodeT->table_size*sizeof(struct list_node *));

Трябва да бъде:

temp = (struct list_node**)realloc(nodeT->table , (nodeT->table_size+1)*sizeof(struct list_node *));

Използвате realloc(), за да добавите място за следващия елемент, но след nodeT->table_size++, стойността на nodeT->table->size е индексът на следващия елемент, тъй като индексът на C масива е базиран на нула, така че броят на елементите трябва да бъде nodeT->table_size + 1.

Това е типична off-by-one грешка.

person Lee Duhem    schedule 05.01.2014