目录
1、int **指针与二维数组问题
01)定义二维数组方法:
int matrix[ROWS][COLUMNS]; //定义一个二维数组,其中ROWS和COLUMNS为常数
02)加入有如下声明的子函数:
void printMatrix(int ** numbers,int rows,int columns);
03)如果直接使用如下方法调用,是错误的;
printMatrix(matrix,ROWS,COLUMNS); //直接这样调用时错误的
原因在于matrix是 int (*)[COLUMNS]类型的,但是函数printMatrix需要的是int **类型的,这两者明显不匹配。
int **从类型上讲是一个指向整型指针的指针,那么如果想要用它来表示一个矩阵需要怎么做呢?因为它的元素是一个指针,如果如果它的每一个元素都表示矩阵的一行,那么它就可以用来表示一个矩阵了。实现代码如下:
![](https://i-blog.csdnimg.cn/blog_migrate/8f900a89c6347c561fdf2122f13be562.gif)
![](https://i-blog.csdnimg.cn/blog_migrate/961ddebeb323a10fe0623af514929fc1.gif)
1 //生成矩阵 2 int ** generateMatrix(int rows,int columns) 3 { 4 int **numbers=new int*[rows]; 5 for(int i=0;i<rows;i++){ 6 numbers[i]=new int[columns]; 7 for(int j=0;j<columns;j++) 8 numbers[i][j]=i*columns+j; 9 } 10 return numbers; 11 }
把int*当做一个整体。它表示创建了一个大小为rows的数组,这个数组的每一个元素代表一个指针。内存布局如下:
这里numbers是一个指向指针的指针,能够用numbers用来表示矩阵的关键就在于使用new关键字分配的内存是连续的,这样number[i]的地址就可以根据numbers的地址计算出来,因为指针变量占据4个字节的内存区域(32位机器)。如果不使用上面的方式分配内存,numbers就真的只是一个指向指针的指针了
04)正确使用printMatrix(matrix,ROWS,COLUMNS)的测试代码:
![](https://i-blog.csdnimg.cn/blog_migrate/8f900a89c6347c561fdf2122f13be562.gif)
![](https://i-blog.csdnimg.cn/blog_migrate/961ddebeb323a10fe0623af514929fc1.gif)
1 #include <stdlib.h> 2 #include <stdio.h> 3 #include <iostream> 4 //打印矩阵 5 void printMatrix(int ** numbers,int rows,int columns){ 6 for(int i=0;i<rows;i++) 7 { 8 for(int j=0;j<columns;j++) 9 std::cout<<numbers[i][j]<<" "; 10 std::cout<<std::endl; 11 } 12 } 13 14 //生成矩阵 15 int ** generateMatrix(int rows,int columns) 16 { 17 int **numbers=new int*[rows]; 18 for(int i=0;i<rows;i++){ 19 numbers[i]=new int[columns]; 20 for(int j=0;j<columns;j++) 21 numbers[i][j]=i*columns+j; 22 } 23 return numbers; 24 } 25 int main(){ 26 int **numbers=generateMatrix(4,5); 27 printMatrix(numbers,4,5); 28 //释放内存 29 for(int i=0;i<4;i++) 30 delete [] numbers[i]; 31 delete numbers; 32 return 0;
参考博客:
https://www.cnblogs.com/lpxblog/tag/C%2B%2B%E9%9D%A2%E8%AF%95%E9%A2%98/
2、memset()和memcpy()
一、memset()用法
void *memset(void *s,int c,size_t n)
作用:将已开辟内存空间 s 的首 n 个字节的值设为值 c(给空间初始化)
C语言需要包含头文件string.h;C++需要包含cstring 或 string.h
![](https://i-blog.csdnimg.cn/blog_migrate/8f900a89c6347c561fdf2122f13be562.gif)
![](https://i-blog.csdnimg.cn/blog_migrate/961ddebeb323a10fe0623af514929fc1.gif)
1 #include <string.h> 2 3 #include <stdio.h> 4 5 #include <memory.h> 6 7 int main(void) 8 9 { 10 11 char buffer[] = "Hello world\n"; 12 13 printf("Buffer before memset: %s\n", buffer); 14 15 memset(buffer, '*', strlen(buffer) ); 16 17 printf("Buffer after memset: %s\n", buffer); 18 19 return 0; 20 21 }
输出结果:
Buffer before memset: Hello world
Buffer after memset: ***********
memset() 函数常用于内存空间初始化。如:
char str[100];
memset(str,0,100);
memset()错误用法:
![](https://i-blog.csdnimg.cn/blog_migrate/8f900a89c6347c561fdf2122f13be562.gif)
![](https://i-blog.csdnimg.cn/blog_migrate/961ddebeb323a10fe0623af514929fc1.gif)
1 int main(void) 2 3 { 4 5 char *buffer = "Hello world\n"; 6 7 printf("Buffer before memset: %s\n", buffer); 8 9 memset(buffer, '*', strlen(buffer) ); 10 11 printf("Buffer after memset: %s\n", buffer); 12 13 return 0; 14 15 }
报错原因:char * buffer = "Hello world\n"; 字符串"Hello world\n"存在于只读存储区,其内容不能被随意更改!!!!
二、memcpy()函数用法
void *memcpy(void *dest, const void *src, size_t n);
C语言需要包含头文件string.h;C++需要包含cstring 或 string.h。
用法:用来将src地址处的内容拷贝n个字节的数据至目标地址dest指向的内存中去。函数返回指向dest的指针。
示例1:
作用:将s中的字符串复制到字符数组d中
![](https://i-blog.csdnimg.cn/blog_migrate/8f900a89c6347c561fdf2122f13be562.gif)
![](https://i-blog.csdnimg.cn/blog_migrate/961ddebeb323a10fe0623af514929fc1.gif)
1 #include <stdio.h> 2 #include <string.h> 3 int main() 4 { 5 char *s="Golden Global View"; 6 char d[20]; 7 clrscr(); 8 memcpy(d,s,( strlen(s)+1) ); 9 printf("%s",d); 10 getchar(); 11 return 0; 12 } 13 输出结果:Golden Global View
示例2:
作用:将s中第14个字符开始的4个连续字符复制到d中。(从0开始)
![](https://i-blog.csdnimg.cn/blog_migrate/8f900a89c6347c561fdf2122f13be562.gif)
![](https://i-blog.csdnimg.cn/blog_migrate/961ddebeb323a10fe0623af514929fc1.gif)
1 #include <string.h> 2 int main( 3 { 4 char *s="Golden Global View"; 5 char d[20]; 6 memcpy(d,s+14,4); //从第14个字符(V)开始复制,连续复制4个字符(View) //memcpy(d,s+14*sizeof(char),4*sizeof(char));也可 7 d[4]='\0'; 8 printf("%s",d); 9 getchar(); 10 return 0; 11 } 12 输出结果: View
示例3:
作用:复制后覆盖原有部分数据;
![](https://i-blog.csdnimg.cn/blog_migrate/8f900a89c6347c561fdf2122f13be562.gif)
![](https://i-blog.csdnimg.cn/blog_migrate/961ddebeb323a10fe0623af514929fc1.gif)
1 #include <stdio.h> 2 #include <string.h> 3 int main(void) 4 { 5 char src[] = "******************************"; 6 char dest[] = "abcdefghijlkmnopqrstuvwxyz0123as6"; 7 printf("destination before memcpy: %s\n", dest); 8 memcpy(dest, src, strlen(src)); 9 printf("destination after memcpy: %s\n", dest); 10 return 0; 11 } 12 输出结果: 13 destination before memcpy:abcdefghijlkmnopqrstuvwxyz0123as6 14 destination after memcpy: ******************************as6
三、注意事项:
memcpy用来做内存拷贝,你可以拿它拷贝任何数据类型的对象,可以指定拷贝的数据长度;例:char a[100],b[50]; memcpy(b, a, sizeof(b));注意如用sizeof(a),会造成b的内存溢出。
另外:strcpy只能拷贝字符串,它遇到'\0'就结束拷贝;例:char a[100],b[50];strcpy(a,b);如用strcpy(b,a),要注意a中的字符串长度(第一个‘\0’之前)是否超过50位,如超过,则会造成b的内存溢出。会造成缓冲区溢出,轻者程序崩溃,重者系统会出现问题!!