1

我使用 gsl 随机生成器生成 2 个大矩阵,并使用 gsl cblas 将它们相乘,但是当 cblas 操作开始时我总是遇到分段错误。当我无法解决这个问题时,我就编写下面的代码,使用非常基本的思想进行矩阵乘法,我仍然得到分段错误,但是当矩阵真的很小时,两者都可以正常工作,我'我对此感到非常困惑。

#include <stdlib.h>
#include <stdio.h>
#include <math.h>
#include <time.h>
#define PI 3.1415926

void GenerateKey(int m, int n, int l, int q, float alpha)
{
    // initialization
    int i;
    int j;
    int k;

    float *A;
    float *S;
    float *E;
    float *B;

    float sigma = (alpha * q ) / sqrt(2 * PI);
    A=(float*)malloc(sizeof(float)*(m*n));
    S=(float*)malloc(sizeof(float)*(n*l));
    B=(float*)malloc(sizeof(float)*(m*l));
    E=(float*)malloc(sizeof(float)*(m*l));

    // init A
    for(i = 0; i < m*n; i++)
    {
        A[i]=0;
    }
    printf("\n");

    // init S
    for(i = 0; i < n*l; i++)
    {
        S[i]=0;
    }

    printf("\n");

    // init E
    for(i = 0; i < m*l; i++)
    {
        E[i]=0;
    }

    printf("\n");
    float po;
    for(i = 0; i < m; i++)
    {
        for(j=0; j<l; j++)
        {      
            po=0;
            for(k=0; k<n; k++)
            {
                po +=A[i*m+k]*S[k*n+j];
            }
            po += E[i*m +j];
            B[i*m+j]=((int)po) % q;
        }
    }

    printf("Game over");

    printf("\n");
    free(A);
    free(B);
    free(S);
    free(E);
}

int main()
{
    GenerateKey(2680,191,64,72973,0.000551);

    return 0;
}
4

3 回答 3

3

当你在做的时候i*m+j,不应该是这样i*l+j吗?同样的i*m+k应该是i*l+kk*n+j应该是k*l+j

原因是,例如E = (float*)malloc(sizeof(float)*(m*l)),所以你有m行和l列(反之亦然),所以如果你正在迭代m维度,你需要将m迭代器(i在这种情况下)乘以矩阵在该维度中的步幅,这是l

于 2012-10-22T13:35:33.437 回答
1

您不检查malloc()返回值,所以我的猜测是一个或多个分配失败并且您正在取消引用NULL. 另一种可能性当然是索引错误,因此您访问越界。

于 2012-10-22T13:30:57.897 回答
1

您错误地计算了所有矩阵的元素索引。

当您有一个MxN分配为一维数组的矩阵时,元素的索引(i,j)i*N+j. 相反,您将其计算为i*M+j.

于 2012-10-22T13:37:29.460 回答