C深刨【指针传参和数组传参】

指针传参和数组传参

一维数组传参

void Show(int a[], int num){
	printf("Show: %d\n", sizeof(a));//这个呢???
}
int main(){
	int a[10] = { 0 };
	printf("main: %d\n", sizeof(a));//求的是整数组的大小
	Show(a,10);
	return 0;
}

回答一个问题,Show函数中sizeof(a)会是多少?
在这里插入图片描述
为什么是4呢?
因为数组传参发生了降维,降维成了指针!!!
为什么降维?
先明确一点,任何函数调用都会形成临时拷贝。因为C是面向过程的语言,在一个程序中就会有很多的函数调用,也会有很多用到数组的场合,数组这么大,每次调用函数都要形成临时拷贝,就会很占用空间,所以C采用降维,降维成指针,这样就避免了数组的临时拷贝,就会大大的提高效率。
那么降维成了什么样的指针了呢?
降维成了指向其内部元素类型的指针!!!!
那为什么就降维成了,指向内部元素类型的指针了呢?
你数组传参是不是每次都传的首元素地址,那用一个和首元素类型一样的指针变量来接收不是理所应当的嘛!
那么数组降维了,会发生临时拷贝吗?
会的,降维成了指针,指针也是数据呀,是数据就要被拷贝,所以用指针变量来接收!!!

在这里插入图片描述

一级指针传参

#include<stdio.h>
void test(char *p)
{
	printf("test: &p = %p\n", &p);
} 
int main()
{
	char *p = "hello world";
	printf("main: &p = %p\n", &p);
	test(p);
	return 0;
}

在这里插入图片描述

结论:在C语言中,只要函数调用,必定发生拷贝。只不过要根据具体情况去决定,拷贝了什么,拷贝了多少!

一道经典的指针传参相关题目

void GetStr(char **pp)
{
	*pp = malloc(sizeof(char)*6);
	if (NULL != *pp){
		strcpy(*pp, "hello");
	}
	else{
		//do nothing!
	}
}
int main()
{
	char *p = NULL;
	GetStr(&p);
	printf("%s\n", p);
	system("pause");
	return 0;
}

在这里插入图片描述

二维数组传参

#include <stdio.h>
#include <windows.h>
void show(char (*p)[4])//二维数组传参也会发生降维,降维成指向其内部元素类型的指针
{
	printf("show: %d\n", sizeof(p));
} 
int main()
{
	char a[3][4] = { 0 };
	printf("main: %d\n", sizeof(a));
	show(a);//数组名首元素地址,即一维数组的地址,类型是char (*)[4]
	return 0;
}

在这里插入图片描述
也会发生临时拷贝哦
那么在传参的时候可以省略数组元素个数嘛
在这里插入图片描述在这里插入图片描述
类型不同所以说,数组的元素个数是数组类型的一部分;

总结:任何维度的数组,传参的时候,都要发生降维,降维成指向其内部元素类型的指针
那么,二维数组,内部“元素”是一维数组!那么降维成指向一维数组的指针
在这里插入图片描述降维成指向内部元素类型的指针,a[3][4][5][6][7],a是一个多维数组,有三个元素每个还是多维数组,传参所以用char (*p)[4][5][6][7],这样的指针接收!!!

函数指针!!!

在这里插入图片描述
函数也是有地址的!!!!
有这两种方法都可以打印地址!!!

#include<stdio.h>
void Show(){
	printf("you can see me\n");
}
int main(){
	Show();
	void(*p)() = Show;//函数指针,指向了一个函数返回类型是void
	(*p)();//解引用p找到函数的地址,调用这个函数
	p();//p是一个指针变量,现在用的是p的右值,即变量的内容,函数的地址数据,故可以调用这个函数
	return 0;
}

函数指针的两种访问方式!!!
一个有趣的代码!(*(void( * )())0)()
在这里插入图片描述

  • 2
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值