Доступ к массиву структур дает ошибку сегментации - PullRequest
0 голосов
/ 14 января 2019

Я реализую алгоритм хеширования с типом пары ключ / значение. Я храню словарь в виде массива записей данных. Я malloc это, но когда я перебираю элементы, которые я только что выделил в функции inicializar_cerrada, программа segfaults на 2-й итерации.

Мои партнеры и я пытались выяснить это, но проблема застряла.

SSCCE:

#include <stdio.h>
#include <stdlib.h>

// ...

#define TAM 11

typedef struct entrada_ {
    int ocupada;
    char clave [LONGITUD_CLAVE];
    char sinonimos [LONGITUD_SINONIMOS];
} entrada;

typedef entrada *tabla_cerrada;

void inicializar_cerrada(tabla_cerrada *diccionario, int tam) {
    int i;
    for (i = 0; i < tam; i++) {
        printf("%d\n", i);
        diccionario[i]->ocupada = 0;
    }
}

int main() {
    tabla_cerrada d = malloc(TAM * sizeof(entrada));    
    inicializar_cerrada(&d, TAM);   
}

Ответы [ 3 ]

0 голосов
/ 14 января 2019

Брось это

typedef entrada *tabla_cerrada;

и просто сделай

void inicializar_cerrada(entrada *diccionario, int tam) {
    int i;
    for (i = 0; i < tam; i++) {
        printf("%d\n", i);
        diccionario[i].ocupada = 0;
    }
}

int main(void) {
    entrada * d = malloc(TAM * sizeof(entrada));    
    inicializar_cerrada(d, TAM);    
}

или даже заставка:

void inicializar_cerrada(entrada *diccionario, size_t tam) {
    for (size_t i = 0; i < tam; ++i) {
        printf("%zu\n", i);
        diccionario[i].ocupada = 0;
    }
}

int main(void) {
    entrada * d = malloc(TAM * sizeof *d);  
    inicializar_cerrada(d, TAM);    
}

Если вы вынуждены использовать

typedef entrada *tabla_cerrada;

сделать

void inicializar_cerrada(tabla_cerrada diccionario, size_t tam) {
    for (size_t i = 0; i < tam; ++i) {
        printf("%zu\n", i);
        diccionario[i].ocupada = 0;
    }
}

int main(void) {
    tabla_cerrada d = malloc(TAM * sizeof *d);  
    inicializar_cerrada(d, TAM);    
}

Тем не менее tabla_cerrada это не "таблица" (она же массив), а указатель. Как я уже сказал, не путайте себя.

0 голосов
/ 14 января 2019
  1. Удалите звездочку из определения функции для аргумента diccionario. tabla_cerrada уже указатель:

    void inicializar_cerrada(tabla_cerrada diccionario, int tam) {

  2. Измените обозначение стрелки на обозначение точки. diccionario[i] - это struct, а не указатель на один:

    diccionario[i].ocupada = 0;

  3. Удалите & из вызова функции, d имеет тип tabla_cerrada, который является указателем:

    inicializar_cerrada(d, TAM);

0 голосов
/ 14 января 2019

@ Герхард прокомментировал :

Вы можете попробовать diccionario [i] -> ocupada => (* diccionario) [i] .ocupada

Отлично сработало!

#include <stdio.h>
#include <stdlib.h>

#define LONGITUD_CLAVE 30
#define LONGITUD_SINONIMOS 300
#define TAM 11

typedef struct entrada_ {
    int ocupada;
    char clave [LONGITUD_CLAVE];
    char sinonimos [LONGITUD_SINONIMOS];
} entrada;

typedef entrada *tabla_cerrada;

void inicializar_cerrada(tabla_cerrada *diccionario, int tam) {
    int i;
    for (i = 0; i < tam; i++) {
        printf("%d\n", i);
        (*diccionario)[i].ocupada = 0;
    }
}

int main() {
    tabla_cerrada d = malloc(TAM * sizeof(entrada));    
    inicializar_cerrada(&d, TAM);   
}
...