C - ошибка сегментации умножения матриц - PullRequest
0 голосов
/ 29 марта 2012

Я получаю ошибку сегментации при запуске этого кода.Кто-нибудь знает почему?Спасибо.

#include <stdio.h>

int main()
{
    double **m1, **m2, **mr;
    int m1_rows, m1_cols, m2_rows, m2_cols, mr_rows, mr_cols;
    int i, j, k;

    printf("Enter number of rows for matrix 1: ");
    scanf("%d", &m1_rows);

    printf("Enter number of columns for matrix 1: ");
    scanf("%d", &m1_cols);

    printf("Enter number of rows for matrix 2: ");
    scanf("%d", &m2_rows);

    printf("Enter number of columns for matrix 2: ");
    scanf("%d", &m2_cols);

    //allocate memory for matrix 1 m1
    m1 = (double **) calloc(m1_rows, sizeof(double *));
    for (i = 0; i < m1_rows; i++) {
        m1[i] = (double *) calloc(m1_cols, sizeof(double));
    }

    //allocate memory for matrix 2 m2
    m2 = (double **) calloc(m2_rows, sizeof(double *));
    for (i = 0; i < m2_rows; i++) {
        m2[i] = (double *) calloc(m2_cols, sizeof(double));
    }

    //allocate memory for sum matrix mr
    mr = (double **) calloc(mr_rows, sizeof(double *));
    for (i = 0; i < mr_rows; i++) {
        mr[i] = (double *) calloc(mr_cols, sizeof(double));
    }

    //assign  mr_rows and mr_cols
    mr_rows = m1_rows;
    mr_cols = m2_cols;

    //initialize product matrix
    for (i = 0; i < m1_rows; i++) {
        for (j = 0; j < m2_cols; j++) {
            mr[i][j] = 0;
        }
    }

    //perform matrix multiplication
    for (i = 0; i < m1_rows; i++) {
        for (j = 0; j < m2_cols; j++) {
            mr[i][j] = 0;
            for (k = 0; k < m1_cols; k++) {
                mr[i][j] += m1[i][k] * m2[k][j];
            }
        }
    }

    //print result
    for (i = 0; i < mr_rows; i++) {
        for (j = 0; j < mr_cols; j++) {
            printf("%f\t", mr[i][j]);
        }
    }

    //free memory m1
    for (i = 0; i < m1_rows; i++); {
        free(m1[i]);
    }
    free(m1);

    //free memory m2
    for (i = 0; i < m2_rows; i++); {
        free(m2[i]);
    }
    free(m2);

    //free memory mr
    for (i = 0; i < mr_rows; i++); {
        free(mr[i]);
    }
    free(mr);

    return 0;
}

Я запустил valgrind valgrind --tool=memcheck a.out для получения дополнительной информации об ошибке сегментации, но в результате было получено более 30000 ошибок, поэтому они не распечатывались.

Ответы [ 2 ]

2 голосов
/ 29 марта 2012

Вы не назначаете mr_rows и mr_cols.Они должны быть установлены следующим образом:

mr_rows = m1_rows;
mr_cols = m2_cols;

Эта строка бесполезна:

mr[i][j] += m1[i][k] * m2[k][j];

Это будет доступ к элементам за пределами, не в последнюю очередь потому, что k не инициализирован,Вам нужна эта строка кода внутри трех вложенных циклов.В самом деле, вы также можете свернуть код обнуления в это.

for(i=0; i<m1_rows; i++){
    for(j=0; j<m2_cols; j++){
        mr[i][j] = 0;
        for(k=0; k<m1_cols; k++){
            mr[i][j] += m1[i][k]*m2[k][j];
        }
    }
}

Кроме того, все ваши циклы освобождения памяти неправильны.Вместо

for(i=0; i<m1_rows; i++);{
    free(m1[i]);
}
free(m1);

должно читаться

for(i=0; i<m1_rows; i++){
    free(m1[i]);
}
free(m1);

Эта беспорядочная точка с запятой убивает вас.

Вам также необходимо проверить, что количество столбцов в m1 равно числу строк в m2, т. Е. Проверить, что m1_cols == m2_rows.

Одна последняя точка.Вы ужасно дублируете свой код здесь.Не используйте три одинаковых цикла for для выделения матрицы и три идентичных цикла for для освобождения.Извлеките эти операции в вспомогательные функции, которые можно вызывать из main.

Это все, что я могу найти!

1 голос
/ 29 марта 2012

Вы нигде не назначаете никаких значений для mr_rows and mr_cols.Таким образом, они будут иметь ненужные значения, и вы будете использовать их для выделения памяти, вызывая calloc().

...