C++ 二维数组传参的四种方式
作者:虚拟笔记使
C++的二维数组里面,通过用数组名传参,传过去后数组名会退化成一个一维数组指针,所以C++的函数参数不能像C语言一样去写,本文主要介绍了C++ 二维数组传参的四种方式,具有一定的参考价值,感兴趣的可以了解一下
最近刚开始刷剑指offer,刚做到第三题的时候,发现C++二维数组的传参方式和C语言略有些不同,所以在这篇博客中,会列出C/C++常见的二维数组传参方式。(本方式和代码都是基于vs环境所编写)
一.C语言二维数组传参方式
C语言二维数组传参一般有三个方式。
1.指针形式接收
#include<stdio.h> void Print1(int* parr, int rows, int cols)//指针,行数,列数 { for (int i = 0; i < rows; i++) { for (int j = 0; j < cols; j++) { printf("%2d ", *(parr + i * cols + j)); } printf("\n"); } printf("\n"); } int main() { int arr[][5] = { {1,2,3,4,5},{6,7,8,9,10},{11,12,13,14,15},{16,17,18,19,20} }; Print1(arr, sizeof(arr) / sizeof(arr[0]), sizeof(arr[0]) / sizeof(arr[0][0])); return 0; }
2. 数组形式接收
#include<stdio.h> void Print2(int parr[][5], int rows, int cols) { for (int i = 0; i < rows; i++) { for (int j = 0; j < cols; j++) { printf("%2d ", parr[i][j]); } printf("\n"); } printf("\n"); } int main() { int arr[][5] = { {1,2,3,4,5},{6,7,8,9,10},{11,12,13,14,15},{16,17,18,19,20} }; Print2(arr, sizeof(arr) / sizeof(arr[0]), sizeof(arr[0]) / sizeof(arr[0][0])); return 0; }
3.数组指针形式接收
void Print3(int(*arr)[5], int rows, int cols) { for (int i = 0; i < rows; i++) { for (int j = 0; j < cols; j++) { printf("%2d ", (*(arr + i))[j]); } printf("\n"); } printf("\n"); } int main() { int arr[][5] = { {1,2,3,4,5},{6,7,8,9,10},{11,12,13,14,15},{16,17,18,19,20} }; Print3(arr, sizeof(arr) / sizeof(arr[0]), sizeof(arr[0]) / sizeof(arr[0][0])); return 0; }
一般来说,第一种更为常见,更加通用,因为第二、三种方法需要在函数中写明二维数组的列数,而一般情况下是不知道的。
二.C++二维数组传参方式
当我写完C语言二维输出传参方式后,接着用C语言写,发现C语言的第一种写法不适用于C++,会直接报错。
原因:
在C语言里面,不管是一维数组还是二维数组,通过用数组名的传参方式,传过去后,数组名都会退化成一个指针指向第一个元素的指针。
而在C++的二维数组里面,通过用数组名传参,传过去后数组名会退化成一个一维数组指针,即这个指针是指向一个一维数组的。
如下图所示:
所以C++的函数参数不能像C语言一样去写。
1. 数组指针形式接收
#include<iostream> using namespace std; void Print1(int (*parr)[5], int rows, int cols) { for (int i = 0; i < rows; i++) { for (int j = 0; j < cols; j++) { cout << (*(parr + i))[j] << " "; } cout << endl; } cout << endl; } int main() { int arr[][5] = { {1,2,3,4,5},{6,7,8,9,10},{11,12,13,14,15},{16,17,18,19,20} }; Print1(arr, sizeof(arr) / sizeof(arr[0]), sizeof(arr[0]) / sizeof(arr[0][0])); return 0; }
2.指针形式接收
第一种方式参数要指明多少列,如果我们不想这样写可以吗,答案是可以的,我们还是可以像C语言的第一种写法一样去写,但是调用函数时的参数需要做出一些改变。
传arr改为传arr[0][0]的地址。
#include<iostream> using namespace std; void Print2(int* parr, int rows, int cols) { for (int i = 0; i < rows; i++) { for (int j = 0; j < cols; j++) { cout << *(parr + i * cols + j) << " "; } cout << endl; } cout << endl; } int main() { int arr[][5] = { {1,2,3,4,5},{6,7,8,9,10},{11,12,13,14,15},{16,17,18,19,20} }; //函数第一个参数改为传arr[0][0]的地址 Print2(&arr[0][0], sizeof(arr) / sizeof(arr[0]), sizeof(arr[0]) / sizeof(arr[0][0])); return 0; }
3. 引用方式传参
void Print3(int(&parr)[4][5],int rows,int cols) { for (int i = 0; i < rows; i++) { for (int j = 0; j < cols; j++) { cout << parr[i][j] << " "; } cout << endl; } cout << endl; } int main() { int arr[][5] = { {1,2,3,4,5},{6,7,8,9,10},{11,12,13,14,15},{16,17,18,19,20} }; Print3(arr, sizeof(arr) / sizeof(arr[0]), sizeof(arr[0]) / sizeof(arr[0][0])); return 0; }
这种引用方式传参要指定行和列,所以也不好用,但是好在C++支持模板,所以可以使用模板来优化。
4.引用+模板
template<size_t row, size_t col> void Print4(int(&parr)[row][col]) { for (int i = 0; i < row; i++) { for (int j = 0; j < col; j++) { cout << parr[i][j] << " "; } cout << endl; } cout << endl; } int main() { int arr[][5] = { {1,2,3,4,5},{6,7,8,9,10},{11,12,13,14,15},{16,17,18,19,20} }; Print4(arr); return 0; }
通过使用引用+模板的方式传参,通过使用模板,编译器会自动推导数组的行数和列数。
到此这篇关于C++ 二维数组传参的四种方式的文章就介绍到这了,更多相关C++ 二维数组传参内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!