Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/arrays/14.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
ANSI C通过指针使用2dim数组_C_Arrays_Pointers_Multidimensional Array - Fatal编程技术网

ANSI C通过指针使用2dim数组

ANSI C通过指针使用2dim数组,c,arrays,pointers,multidimensional-array,C,Arrays,Pointers,Multidimensional Array,很久很久以前,我玩了很多次C,但都忘了。现在我试图解决简单的任务,但失败了 我想写一个函数,它接受2dim数组或char*并打印它。但是我的代码有缺陷,我不明白为什么。据我所知,products是指向2dim数组的指针,所以将它增加到I*sizeof(char**)我得到指向子数组的指针,增加子数组指针我得到指向char块的指针。但我的代码看起来好像是在寻找不同的内存块 关于产品数组-我知道它有N行和2列 #include <stdio.h> #include <string.

很久很久以前,我玩了很多次
C
,但都忘了。现在我试图解决简单的任务,但失败了

我想写一个函数,它接受2dim数组或
char*
并打印它。但是我的代码有缺陷,我不明白为什么。据我所知,
products
是指向2dim数组的指针,所以将它增加到
I*sizeof(char**)
我得到指向子数组的指针,增加子数组指针我得到指向char块的指针。但我的代码看起来好像是在寻找不同的内存块

关于
产品
数组-我知道它有N行和2列

#include <stdio.h>
#include <string.h>

void print(char*** products, size_t rows, size_t cols) {
    size_t i;

    for(i = 0; i < rows; i++) {
        printf("Col1: '%s. Col2: %s'\n",
            (products + i * sizeof(char**)),
            (products + i * sizeof(char**) + sizeof(char*))
        );
    }
}

int main(void) {
    const char* a[][3] = {{"abc", "1"}, {"def", "2"}, {"ghi", "3"}};
    print((char***)a, 3, 2);

    return 0;
}
#包括
#包括
无效打印(字符***产品、大小行、大小列){
尺寸i;
对于(i=0;i
此声明中定义的数组

const char* a[][3] = {{"abc", "1"}, {"def", "2"}, {"ghi", "3"}};
#include <stdio.h>
#include <string.h>

#define N 3

void print1( const char *product[][N], size_t rows )
{

    for ( size_t i = 0; i < rows; i++ ) 
    {
        for ( const char **p = product[i]; *p; ++p )
        {
            printf( "%s ", *p );
        }
        printf( "\n" );
    }
}    

void print2( size_t rows, size_t cols, const char *product[rows][cols] )
{

    for ( size_t i = 0; i < rows; i++ ) 
    {
        for ( const char **p = product[i]; *p; ++p )
        {
            printf( "%s ", *p );
        }
        printf( "\n" );
    }
}    


int main( void )
{
    const char * a[][N] = 
    {
        { "abc", "1" }, 
        { "def", "2" }, 
        { "ghi", "3" }
    };

    print1( a, N );
    printf( "\n" );

    size_t n = N;

    const char * b[n][n];

    memcpy( b, a, sizeof( a ) );

    print2( n, n, b );
    printf( "\n" );
}    
具有类型
常量字符*[3][3]

考虑到数组有三个“列”,在数组声明中显式指定了三个列

const char* a[][3] =....
               ^^^
最后一列中的元素由
NULL
初始化

当数组在表达式中用作参数时,它会显式转换为指向其第一个元素的指针

也就是说,如果使用上面显示的数组作为参数,那么它将转换为类型

const char * ( * )[3]
它与
char***

所以函数应该声明为like

void print( const char * ( *products )[3], size_t rows );
或者

void print( const char * products[][3], size_t rows );
函数的调用应该像

print( a, 3 );
print( a, 3, 2 );
print( 3, 3, a );
您可以再指定一个参数来设置要输出的列数(例如)

void print( const char * ( *products )[3], size_t rows, size_t cols );
在这种情况下,可以像这样调用函数

print( a, 3 );
print( a, 3, 2 );
print( 3, 3, a );
但是,数组本身在任何情况下都有3列。:)

或者如果编译器支持可变长度数组,如

void print( size_t rows, size_t cols, const char * ( *products )[cols] );
还是为了可读性

void print( size_t rows, size_t cols, const char * products[rows][cols] );
它可以被称为

print( a, 3 );
print( a, 3, 2 );
print( 3, 3, a );
下面是一个演示程序,它显示了函数声明的两种方式

const char* a[][3] = {{"abc", "1"}, {"def", "2"}, {"ghi", "3"}};
#include <stdio.h>
#include <string.h>

#define N 3

void print1( const char *product[][N], size_t rows )
{

    for ( size_t i = 0; i < rows; i++ ) 
    {
        for ( const char **p = product[i]; *p; ++p )
        {
            printf( "%s ", *p );
        }
        printf( "\n" );
    }
}    

void print2( size_t rows, size_t cols, const char *product[rows][cols] )
{

    for ( size_t i = 0; i < rows; i++ ) 
    {
        for ( const char **p = product[i]; *p; ++p )
        {
            printf( "%s ", *p );
        }
        printf( "\n" );
    }
}    


int main( void )
{
    const char * a[][N] = 
    {
        { "abc", "1" }, 
        { "def", "2" }, 
        { "ghi", "3" }
    };

    print1( a, N );
    printf( "\n" );

    size_t n = N;

    const char * b[n][n];

    memcpy( b, a, sizeof( a ) );

    print2( n, n, b );
    printf( "\n" );
}    

考虑到,如果编译器支持可变长度数组,则可能无法初始化它们,然后定义它们。

此声明中定义的数组

const char* a[][3] = {{"abc", "1"}, {"def", "2"}, {"ghi", "3"}};
#include <stdio.h>
#include <string.h>

#define N 3

void print1( const char *product[][N], size_t rows )
{

    for ( size_t i = 0; i < rows; i++ ) 
    {
        for ( const char **p = product[i]; *p; ++p )
        {
            printf( "%s ", *p );
        }
        printf( "\n" );
    }
}    

void print2( size_t rows, size_t cols, const char *product[rows][cols] )
{

    for ( size_t i = 0; i < rows; i++ ) 
    {
        for ( const char **p = product[i]; *p; ++p )
        {
            printf( "%s ", *p );
        }
        printf( "\n" );
    }
}    


int main( void )
{
    const char * a[][N] = 
    {
        { "abc", "1" }, 
        { "def", "2" }, 
        { "ghi", "3" }
    };

    print1( a, N );
    printf( "\n" );

    size_t n = N;

    const char * b[n][n];

    memcpy( b, a, sizeof( a ) );

    print2( n, n, b );
    printf( "\n" );
}    
具有类型
常量字符*[3][3]

考虑到数组有三个“列”,在数组声明中显式指定了三个列

const char* a[][3] =....
               ^^^
最后一列中的元素由
NULL
初始化

当数组在表达式中用作参数时,它会显式转换为指向其第一个元素的指针

也就是说,如果使用上面显示的数组作为参数,那么它将转换为类型

const char * ( * )[3]
它与
char***

所以函数应该声明为like

void print( const char * ( *products )[3], size_t rows );
或者

void print( const char * products[][3], size_t rows );
函数的调用应该像

print( a, 3 );
print( a, 3, 2 );
print( 3, 3, a );
您可以再指定一个参数来设置要输出的列数(例如)

void print( const char * ( *products )[3], size_t rows, size_t cols );
在这种情况下,可以像这样调用函数

print( a, 3 );
print( a, 3, 2 );
print( 3, 3, a );
但是,数组本身在任何情况下都有3列。:)

或者如果编译器支持可变长度数组,如

void print( size_t rows, size_t cols, const char * ( *products )[cols] );
还是为了可读性

void print( size_t rows, size_t cols, const char * products[rows][cols] );
它可以被称为

print( a, 3 );
print( a, 3, 2 );
print( 3, 3, a );
下面是一个演示程序,它显示了函数声明的两种方式

const char* a[][3] = {{"abc", "1"}, {"def", "2"}, {"ghi", "3"}};
#include <stdio.h>
#include <string.h>

#define N 3

void print1( const char *product[][N], size_t rows )
{

    for ( size_t i = 0; i < rows; i++ ) 
    {
        for ( const char **p = product[i]; *p; ++p )
        {
            printf( "%s ", *p );
        }
        printf( "\n" );
    }
}    

void print2( size_t rows, size_t cols, const char *product[rows][cols] )
{

    for ( size_t i = 0; i < rows; i++ ) 
    {
        for ( const char **p = product[i]; *p; ++p )
        {
            printf( "%s ", *p );
        }
        printf( "\n" );
    }
}    


int main( void )
{
    const char * a[][N] = 
    {
        { "abc", "1" }, 
        { "def", "2" }, 
        { "ghi", "3" }
    };

    print1( a, N );
    printf( "\n" );

    size_t n = N;

    const char * b[n][n];

    memcpy( b, a, sizeof( a ) );

    print2( n, n, b );
    printf( "\n" );
}    
考虑到可变长度数组(如果编译器支持)可能未初始化,则定义它们

const char*a[][3]={{{“abc”,“1”},{“def”,“2”},{“ghi”,“3”}

在这种情况下,您实际上可以编写:

const char* a[][2] = {{"abc", "1"}, {"def", "2"}, {"ghi", "3"}};
但是如果你真的想要一个3列数组,你应该告诉print有3列,而不是2列。但是你的打印只能打印前两列当然

然后,任何
T
的N维数组都可以看作是
T
的简单1D数组。您只需进行一些地址计算即可访问所需的元素。一旦有了指向数组第一项的指针,就可以这样做。下面是一个工作版本:

#include <stdio.h>
#include <string.h>

typedef const char * T;

void print(T *products, size_t rows, size_t cols) {
    size_t i;

    for (i = 0; i < rows; i++) {
        // Each row has cols items so here is the current row (i-th row):
        T *row = products + i * cols;
        printf("{%s, %s}\n", row[0], row[1]);
    }
}

int main(void) {
    T a[][3] = { { "abc", "1" }, { "def", "2" }, { "ghi", "3" } };

    // Tell print that there are 3 cols, not 2
    print(&a[0][0], 3, 3);

    return 0;
}
#包括
#包括
typedef const char*T;
无效打印(T*产品、大小行、大小列){
尺寸i;
对于(i=0;i
const char*a[][3]={{{“abc”,“1”},{“def”,“2”},{“ghi”,“3”}

在这种情况下,您实际上可以编写:

const char* a[][2] = {{"abc", "1"}, {"def", "2"}, {"ghi", "3"}};
但是如果你真的想要一个3列数组,你应该告诉print有3列,而不是2列。但是你的打印只能打印前两列当然

然后,任何
T
的N维数组都可以看作是
T
的简单1D数组。您只需进行一些地址计算即可访问所需的元素。一旦有了指向数组第一项的指针,就可以这样做。下面是一个工作版本:

#include <stdio.h>
#include <string.h>

typedef const char * T;

void print(T *products, size_t rows, size_t cols) {
    size_t i;

    for (i = 0; i < rows; i++) {
        // Each row has cols items so here is the current row (i-th row):
        T *row = products + i * cols;
        printf("{%s, %s}\n", row[0], row[1]);
    }
}

int main(void) {
    T a[][3] = { { "abc", "1" }, { "def", "2" }, { "ghi", "3" } };

    // Tell print that there are 3 cols, not 2
    print(&a[0][0], 3, 3);

    return 0;
}
#包括
#包括
typedef const char*T;
无效打印(T*产品、大小行、大小列){
尺寸i;
对于(i=0;i
您已经混淆了您所认为的列和行。解决这个问题,然后摆脱三星级的胡说八道,让函数接受可变数量的列,结果如下:

#include <stdio.h>

void print(size_t rows, size_t cols, const char* products[rows][cols]) 
{
  for(size_t r=0; r<rows; r++) 
  {
    for(size_t c=0; c<cols; c++)
    {
      printf("Col%zu: %s. ", c, products[r][c]);
    }
    printf("\n");
  }
}

int main (void) 
{
  const char* a[3][2] = {{"abc", "1"}, {"def", "2"}, {"ghi", "3"}};
  print(3, 2, a);

  return 0;
}
#包括
空白打印(si)