2014-05-25 177 views
2

我正在尝试对矩阵矩阵乘法进行编码,并且在几次试验后,每隔几个试验后它都会继续给出分段错误。 我在网站上查找了不同的问题,并尝试了以下两种代码的几种方法。动态分配矩阵C进行乘法运算

此外,为什么我们需要指向“int指针指针”的指针,如int ** mat1,** mat2等?我不知道为什么要这样做,但我在一些答案中看到了它。

代码1

void mxmult() 
{ 
    int n,m,a,b,c,d, sum=0; 
    int x,y,z; 
    printf("Enter first order [n*n]\n"); 
    scanf("%d", &n); 
    printf("Enter second order [m*m]\n"); 
    scanf("%d", &m); 
    if (n!=m) 
    { 
     printf("Invalid orders"); 

    } 
    else 
    { 
     //mem allocate for matrix 1 
     int **mat1 = (int**)malloc(n*sizeof(int)); 
     for(x=0;x<n;x++) 
      { 
       mat1[x]=(int*)malloc(n*sizeof(int)); 
      } 
     // input matrix 1 
     printf("Enter the first matrix entries\n"); 
     for (a = 0; a <n; a++) 
     { 
      for (b = 0; b < n; b++) 
      { 
       scanf("%d", &mat1[a][b]); 
      } 
     } 
     // memory allocate matrix 2 
     int **mat2 = (int**)malloc(m*sizeof(int)); 
     for(y=0;y<n;y++) 
      { 
       mat2[y]=(int*)malloc(m*sizeof(int)); 
      } 

     //inpur matrix 2 
     printf("Enter the second matrix entries\n"); 
     for (c = 0; c <n; c++) 
     { 
      for (d= 0; d < n; d++) 
      { 
       scanf("%d", &mat2[c][d]); 
      } 
     } 

     //Memory allocate matrix Mult 
     int **mult=(int**)malloc(m*sizeof(int)); 
     for(z=0;z<m;z++) 
      mult[z]=(int*)malloc(m*sizeof(int)); 
     for (a = 0; a < n; a++) 
     { 
      for (d = 0; d < m; d++) 
      { 
       for (c = 0; c < n; c++) 
       { 
        sum=sum + (mat1[a][c] *mat2[c][d]); 
       } 
       mult[a][d] = sum; 
       sum= 0; 
      } 
     } 
     printf("Product\n"); 

     for (a = 0 ; a < n ; a++) 
     { 
      for (d = 0 ; d < m ; d++) 
       printf("%d\t", mult[a][d]); 
      printf("\n"); 
     } 

    } 
} 

代码2:

void mxmult() 
{ 
    int n,m,a,b,c,d, sum=0; 
    int x,y,z; 
    printf("Enter first order [n*n]\n"); 
    scanf("%d", &n); 
    printf("Enter second order [m*m]\n"); 
    scanf("%d", &m); 
    if (n!=m) 
    { 
     printf("Invalid orders"); 

    } 
    else 
    { 
     //mem allocate for matrix 1 
     int **mat1 = (int**)malloc(n*n*sizeof(int)); 

     // input matrix 1 
     printf("Enter the first matrix entries\n"); 
     for (a = 0; a <n; a++) 
     { 
      for (b = 0; b < n; b++) 
      { 
       scanf("%d", &mat1[a][b]); 
      } 
     } 
     // memory allocate matrix 2 
     int **mat2 = (int**)malloc(m*m*sizeof(int)); 

      //input matrix 2 
     printf("Enter the second matrix entries\n"); 
     for (c = 0; c <n; c++) 
     { 
      for (d= 0; d < n; d++) 
      { 
       scanf("%d", &mat2[c][d]); 
      } 
     } 

     //Memory allocate matrix Mult 
     int **mult=(int**)malloc(m*m*sizeof(int)); 

      // Mx multiplicatn 
     for (a = 0; a < n; a++) 
     { 
      for (d = 0; d < m; d++) 
      { 
       for (c = 0; c < n; c++) 
       { 
        sum=sum + (mat1[a][c] *mat2[c][d]); 
       } 
       mult[a][d] = sum; 
       sum= 0; 
      } 
     } 
     printf("Product\n"); 

     for (a = 0 ; a < n ; a++) 
     { 
      for (d = 0 ; d < m ; d++) 
       printf("%d\t", mult[a][d]); 
      printf("\n"); 
     } 

    } 
} 

我一直在努力执行代码2,然后,码2。两人都是在几次战斗后才给出赛格缺陷。

+0

不知道,但是这看起来不正确:'scanf函数( “%d”,&MAT1 [A] [B] )'。因为mat1已经是一个指针了,所以你不应该使用&符号。 – MightyPork

+1

'int ** mat1 =(int **)malloc(n * sizeof(int));' - >'int ** mat1 =(int **)malloc(n * sizeof(int *));' – BLUEPIXY

+0

int * mat1 =(int **)malloc(n * n * sizeof(int));' - >'int(* mat1)[n] = malloc(n * n * sizeof(int));'' – BLUEPIXY

回答

9

int **类型是什么被称为衣衫褴褛的阵列。通过首先分配一个“脊柱”数组来创建一个不规则数组,该数组包含指向每个“肋骨”的指针。当您参考matrix[x][y]时,您在“脊椎”中取指针x处的指针,然后在“肋骨”中获取索引“y”处的元素。下面是示出了该结构的漂亮的图:

Ragged array in C

可以读取comp.lang.c FAQ list · Question 6.16: How can I dynamically allocate a multidimensional array?获得更多信息(也上述图像的源)。

另一种选择是实际为您的矩阵分配一个二维数组(我的首选方法)。这要求编译器支持一些C99结构,但除Microsoft C编译器(例如gcc和clang)之外的所有主要编译器似乎都默认支持这种编译器。这里有一个例子:

int (*matrix)[colCount] = (int(*)[colCount]) malloc(sizeof(int)*rowCount*colCount); 

上面的奇怪的语法是你如何declare a pointer to an array in C。需要围绕*matrix的括号来从declaring from an array of pointers中消除歧义。 You don't need to cast the result of malloc in C,所以等效:

int (*matrix)[colCount] = malloc(sizeof(int)*rowCount*colCount); 

该分配的存储器中的单个块的矩阵,并且由于编译器知道每行(即colCount)的长度,它可以插入数学计算用于任何适当的地址2D参考。例如,matrix[x][y]相当于((int*)matrix)[x*colCount+y]

我更喜欢分配一个二维数组,因为您可以在一行中完成所有的分配,而对于不整齐的数组,您必须单独设置指向每一行的指针,这通常需要另一条线路作为循环。


至于你的内存设计缺陷,这一行看起来可疑:

int **mat1 = (int**)malloc(n*sizeof(int)); 

由于mat1是类型int**,在mat1每个条目应该是一个int*。但是,您的malloc正在使用sizeof(int)为条目分配内存!试试这个:

int **mat1 = (int**)malloc(n*sizeof(int*)); 

假设你是一个64位系统上,sizeof(int)大概是4(字节),而sizeof(int*)应为8(字节)。这意味着目前您正在分配内存的一半,因为您需要,这意味着当您访问该阵列的后半部分中的条目时会发生坏事。使用正确的尺寸(sizeof(int*))应该解决这个问题。

(可能还有其他的问题太多,但就是这样乍一看站出来的人。)