【问题标题】:Passing 2d array to function with pointer使用指针将二维数组传递给函数
【发布时间】:2020-08-16 20:53:37
【问题描述】:

谁能解释一下 print() 函数有什么问题?

printf("Control") 从不工作,输出是分段错误 11

int main(int argc, char **argv){
int m=5,n=4;    // matrix[5][4]
int a=50,b=20;  // range: 20-50

int **matrix;

imatrix(matrix,m,n,a,b);
print(matrix,m,n);

第一步:用值填充地址

    void imatrix(int **matrix,int m,int n,int max, int min){
    srand(time(NULL));
    int i=0,j=0;
    
    matrix = (int **)malloc( m * sizeof(int*) );
    if( matrix == NULL ){
        printf( "memory req.!" );
    }
    
    
    for( i = 0; i < m; i++ ) {
        matrix[i] = (int *)malloc( n * sizeof(int) );
        if( matrix[i] == NULL ){
            printf( "memory req.!" );
        }
    }
    
    
    for(i=0;i<m;i++){
        for(j=0;j<n;j++){
            matrix[i][j]=(rand()%(max-min))+min;
            printf("%2d ",matrix[i][j]);
        }
        printf("\n\n");
    }
    }

到这里为止一切正常。 我得到分段错误:下面的代码和“控制”行之后的 11 永远不起作用

void print(int **matrix, int m, int n){
int i,j;
for(i=0; i < m; i++){
    for(j=0; j < n; j++){
       printf("%d",*(*(matrix + i) + j));
    }
    printf("\n");
}

printf("control");
}

【问题讨论】:

    标签: c segmentation-fault dynamic-memory-allocation


    【解决方案1】:

    不是printf("control") 会导致段错误(尽管最好不要使用printf:考虑将其更改为puts("control"),这也会输出换行符。)这是之前的尝试打印取消引用未初始化值的矩阵。

    发生这种情况是因为您的 imatrix 函数没有返回它创建的矩阵,并且您的 main 中的 matrix 没有被赋予任何值。

    事实上,imatrix 不返回任何内容,因为它被定义为返回 void。它需要一个matrix 参数,我想它是一个输出参数,但是:

    • 那个参数有错误的类型作为输出参数(输出参数需要是一个指针要返回的对象;)

    • 它从不尝试使用指向要返回的对象的指针来返回对象。

    为了符合这些要求,您需要原型

    void imatrix(int*** matrix, int m, int n, int max, int min);
    

    而且您必须为每次使用 matrix [注 1] 添加额外的间接级别:

        *matrix = malloc(m * sizeof(**matrix));
        if (*matrix == NULL) {
            printf( "memory req.!" );
            /* NOTE: You shouldn't attempt to continue after the malloc fails.
             * Return immediately and let the caller deal with the malloc failure.
             */
        }
    
        for( i = 0; i < m; i++ ) {
            (*matrix)[i] = malloc( n * sizeof(*(*matrix)[i])) );
            if( (*matrix)[i] == NULL ){
        // etc.
    

    我认为我们可以同意这是一个主要的 PITA,除非必要,否则不值得麻烦。

    就个人而言,我发现除非绝对必要,否则根本不使用输出参数不会让人感到困惑。在这种情况下,根本没有必要,因为您可以只返回指针来分配内存:

    /* CHANGE: Prototype */
    int** imatrix(int m, int n, int max, int min){
        srand(time(NULL)); /* TODO: This initialisation should really be done in main */
        int i=0, j=0;
        
        /* CHANGE: matrix is a local variable */
        int** matrix = malloc( m * sizeof(*matrix) );
        /* CHANGE: Immediate return on malloc failure */
        if( matrix == NULL ) {
            return matrix;
        }
        
        for( i = 0; i < m; i++ ) {
            matrix[i] = malloc( n * sizeof(*matrix[i]) );
            if( matrix[i] == NULL ){
                printf( "memory req.!" );
            }
        }
        
        
        for(i=0;i<m;i++){
            for(j=0;j<n;j++){
                matrix[i][j]=(rand()%(max-min))+min;
                printf("%2d ",matrix[i][j]);
            }
            printf("\n\n");
        }
    
        /* CHANGE: matrix is returned */
        return matrix;
    }
    

    使用模式略有不同:

    int main(int argc, char **argv){
        int m=5, n=4;    // matrix[5][4]
        int a=50, b=20;  // range: 20-50
    
        /* CHANGE: imatrix returns the new matrix */
        int **matrix = imatrix(m, n, a, b);
        /* CHANGE: check for failure */
        if (matrix == NULL) {
             fprintf(stderr, "%s\n", "imatrix failed to allocate memory.");
             exit(1);
        }
    
        print(matrix, m, n);
        /* TODO: Free the storage allocated for matrix */
    }
    

    注意事项

    1. 在这段代码中,我改变了 malloc 的用法:

      lvalue = (RedundantCast*)malloc(count * sizeof(FixedType));
      

      到惯用的 C:

      lvalue = malloc(count * sizeof(*lvalue));
      

      malloc 的返回值的显式转换在 C 中充其量是没有意义的,因为 malloc 返回一个 void* 并且 C 很乐意自动将 void* 转换为任何类型的指针。使用目标 (sizeof(*lvalue)) 指向的对象类型而不是插入特定类型可以保护您免受将来编辑中类型更改的可能性,并且您忘记在所有对 @987654342 的调用中进行更改@。 (例如,考虑将matrix 设为long long 而不是int 的矩阵会发生什么。)

    【讨论】:

      猜你喜欢
      • 2016-04-27
      • 1970-01-01
      • 2014-05-09
      • 1970-01-01
      • 1970-01-01
      • 2019-03-28
      • 1970-01-01
      • 2021-04-15
      • 1970-01-01
      相关资源
      最近更新 更多