C++ 是否可以编写一个可以接受n维数组的函数?
我正在尝试编写一个函数,它可以获取任意维度的数组并成功地打印数组中的值。但我不能向前推进,因为在声明函数时,我们必须声明除最左边的维度之外的所有维度。我们是否有可能写出一个广义函数,它可以将数组作为任意维的输入C++ 是否可以编写一个可以接受n维数组的函数?,c++,c,C++,C,我正在尝试编写一个函数,它可以获取任意维度的数组并成功地打印数组中的值。但我不能向前推进,因为在声明函数时,我们必须声明除最左边的维度之外的所有维度。我们是否有可能写出一个广义函数,它可以将数组作为任意维的输入 例如,该函数应该能够采用二维数组、三维数组或n维数组,其中n是任意数。如果将数组编码为一维,然后自己计算单个索引,则肯定可以让一个程序执行操作,就好像该数组是为可变数量的维度创建的一样 我最初的想法是从一个向量开始,该向量包含您打算使用的每个维度的范围 该向量中的元素数就是您拥有的维度数
例如,该函数应该能够采用二维数组、三维数组或n维数组,其中n是任意数。如果将数组编码为一维,然后自己计算单个索引,则肯定可以让一个程序执行操作,就好像该数组是为可变数量的维度创建的一样 我最初的想法是从一个向量开始,该向量包含您打算使用的每个维度的范围 该向量中的元素数就是您拥有的维度数。对每个维度和模板使用递归(在C++中也是如此),下面可能会有所帮助:
template <typename T>
void print(const T&e)
{
std::cout << e << " ";
}
template <typename T, std::size_t N>
void print(const T (&a)[N])
{
std::cout << "{";
for (const auto& e : a) {
print(e);
}
std::cout << "}" << std::endl;
}
数组作为指向数组元素类型的指针传递给函数,而与数组的维数无关。您可以使用更多参数来指定维度数n,以及长度为n的数组(另一个数组)来指定每个维度中的元素数。请注意,[]表示法只是执行指针添加的一种简洁方式。我确信这至少违反了C标准的一条规则,但在实践中应该可以使用。请注意,它使用0作为数组任何级别的终止元素的前哨值
void print(void* p, int dim)
{
if (dim == 1)
{
int* a = (int*) p;
while (*a)
{
printf("%d ", *a++);
}
printf("\n");
}
else
{
void** a = (void**)p;
while (*a)
{
print(*a++, dim - 1);
}
}
}
void test()
{
int x0 [] = { 11, 12, 13, 14, 15, 0 };
int x1 [] = { 21, 22, 23, 0 };
int x2 [] = { 0 };
int x3 [] = { 41, 42, 0 };
int x4 [] = { 51, 52, 53, 0 };
int* y0 [] = { x0, x3, 0 };
int* y1 [] = { 0 };
int* y2 [] = { x1, x2, x4, 0 };
int** z [] = { y0, y1, y2, 0 };
print(z, 3);
}
印刷品:
11 12 13 14 15
41 42
21 22 23
51 52 53
如果要访问特定元素或对数组进行操作,但要动态创建矩阵,则可以使用指针通过在print函数中传递维度来访问每个元素 因为如果将多维数组定义为
int[][]
,那么
x=y[a][b]
相当于x=*((int*)y+a*列数+b)代码>
查看此帖子了解更多详细信息:
因此,如果要打印整个矩阵或访问任何特定元素,可以执行以下操作:
#include <iostream>
using namespace std;
//the function print_2D_matrix receives 4 arguments: pointer to first element
// dimension of array arr, i.e. n x m
// index of the element to be printed, i.e. a and b
void print_2D_matrix(int *arr, int n, int m, int a, int b){
for(int i = 0; i < n; i++){
for(int j = 0; j < m; j++)
printf("%d ", *(arr + (i * m) + j));
printf("\n");
}
//go to the address just before a row, i.e. (a - 1) * NO_OF_COLUMNS
//then go to the address on b column, i.e. (a - 1) * NO_OF_COLUMNS + b
//since we started from the base address, i.e. first element( arr[0][0] ), subtract 1
printf("arr[3][3] = %d\n", *(arr + ((a - 1) * m) + b - 1)); //print arr[a][b]
}
int main() {
int n, m;
cin>>n>>m;
int arr[n][m];
for(int i = 0; i < n; i++) //initialize the matrix
for(int j = 0; j < m; j++)
arr[i][j] = i * j;
print_2D_matrix((int *) arr, n, m, 3, 3);
return 0;
}
有可能。您可能能够以某种方式使用模板,但这会使程序出错,特别是因为听起来您是在与团队合作。@JoachimPileborg这取决于生成是随机的还是预定义的;一个可变的模板可以为预定义的非随机的工作。答案似乎也取决于这是C还是C++问题,因为我不认为C中存在模板。这适用于支持C++ 11的编译器。@ RayDelmiRAND:如果需要的话,for范围可以被写入C++ 03(简单的<代码>打印(A[i]);< /Cord>).你能告诉我怎么走吗?我不知道。@RaydelMiranda:for(std::size_t I=0;I!=N;++I){print(a[I])}
我知道你可以这样写,但同样,你发布的代码只有在编译器支持c++11的情况下才能编译。不是批评家,它只是对读者的警告。请在投票时发表评论。您可以添加一些const
。
#include <iostream>
using namespace std;
//the function print_2D_matrix receives 4 arguments: pointer to first element
// dimension of array arr, i.e. n x m
// index of the element to be printed, i.e. a and b
void print_2D_matrix(int *arr, int n, int m, int a, int b){
for(int i = 0; i < n; i++){
for(int j = 0; j < m; j++)
printf("%d ", *(arr + (i * m) + j));
printf("\n");
}
//go to the address just before a row, i.e. (a - 1) * NO_OF_COLUMNS
//then go to the address on b column, i.e. (a - 1) * NO_OF_COLUMNS + b
//since we started from the base address, i.e. first element( arr[0][0] ), subtract 1
printf("arr[3][3] = %d\n", *(arr + ((a - 1) * m) + b - 1)); //print arr[a][b]
}
int main() {
int n, m;
cin>>n>>m;
int arr[n][m];
for(int i = 0; i < n; i++) //initialize the matrix
for(int j = 0; j < m; j++)
arr[i][j] = i * j;
print_2D_matrix((int *) arr, n, m, 3, 3);
return 0;
}
0 0 0 0 0
0 1 2 3 4
0 2 4 6 8
0 3 6 9 12
arr[3][3] = 4