C++——指针、右左法则、指针和函数的关系、函数指针、函数转移表(函数指针static)

目录

一、指针

1、定义

2、 分类

二、右左法则 

三、函数指针 

(1)函数名——代表函数的入口地址(2) 函数指针的用法

(3)函数指针举例

(4)扩展:函数转移表

四、思考题

一、指针

1、定义

  • 指针是一个特殊的变量,它里面存储的数值被解释成为内存里的一个地址
  • 指针的四方面的内容:指针的类型、指针所指向的类型、指针的值或者叫指针所指向的内存区、指针本身所占据的内存区。
  • 指针变量:指向存放地址的变量(特殊的变量)。
    基类型:* 指针变量名。
  • 接下来看一个例子,输出结果是多少? 
int main()
{
	char a[] = "123";
	char b[] = "123";
	const char c[] = "123";
	const char d[] = "123";
	const char* p1 = "123";
	const char* p2 = "123";
	const char* const p3 = "123";
	const char* const p4 = "123";
	if (a == b)
		cout << "a==b" << endl;//error,数组存储字符串,会开辟新的空间,表示的地址不同
	if (a == c)
		cout << "a==c" << endl;//error
	if (c == d)
		cout << "c==d" << endl;//error
	if (p1 == p2)
		cout << "p1==p2" << endl;//true,指向字符串常量区,指向字符串的首地址。
	if (p3 == p4)
		cout << "p3==p4" << endl;//
	if (p1 == p3)
		cout << "p1==p3" << endl;//

}
  • 运行结果如下:
  • 因为abcd是数组,数组存储字符串,会开辟新的空间,所以abcd表示的地址各不相同。 
  • p1,p2,p3是指针,指针指向字符串常量区,指向字符串所在的首地址,所以p1p2p3指向的地址是同一个,故相等。

 

2、 分类

单指针、双指针、指针数组、数组指针、指针函数、函数指针
①单指针:变量、一维数组、二维数组、函数
②双指针:变量、指针数组
③字符指针

二、右左法则 

方法:
//先看标志符,往右看一个再往左看一个

举例:
①int (*p)[4]——p是整型数指针——数组指针——指向数组的指针//先找标志符,看p,跟星号相结合,p是指针

②int *q[4];——q是指针数组——存储指针的数组//q是数组名,后面直接跟[]

int (*p1[5])——p1是指针数组,括号里没有函数

int *(*p2[3])(int)——p2是指针函数指针数组

int *p3(int n)——p3是指针函数,返回值为指针的函数

int (*p4)(int,int)——p4是函数指针,指向函数的指针

三、函数指针 

(1)函数名——代表函数的入口地址
(2) 函数指针的用法


 ①指针指向函数,由指针调用函数
 ②函数指针作为另外一个函数的参数
 ③函数指针组作为另外一个函数的返回值

(3)函数指针举例

         函数指针函数 fn是个函数名,函数里面有int n的一个参数,fn函数的返回值是个指针,
这个指针指向一类函数 int xx(int,int)。

int (*fn(int n))(int, int)//函数指针函数
{
	cout << "fn n=" << n << endl;
	return min;//返回值是个指向函数的指针,在此可以返回函数名
}
int main()
{
	int (*p)(int, int);//函数指针,p是一个指针,指向一类函数,函数有两个int型参数,返回值为int
	p = Sum;
	cout << Sum(4, 7) << endl;
	cout << p(3, 6) << endl;
	test(2, 9, max);//将max传给p,相当于p=max;p->max

	cout << "函数指针作为函数返回值:" << endl;
	//cout<<fn(100)(3, 20)<<endl;//先调用fn函数,将100传递给参数,fn函数返回min,在调用min(3,20)
	p=fn(100);//p=min
	cout << p(3, 20) << endl;
}

(4)扩展:函数转移表

  • 转移表就是一个函数指针数组,声明并初始化一个数组。
  •  确保函数原型出现在这个数组声明之前,在使用转移表这个指针数组时特别要注意下标引用不要越界,否则会引起不可预知的后果。 
  • 函数在被使用时总是由编译器把它转换为函数指针。

四、思考题

  • 用构造函数求解:1+2+3+4...+100
  • 要求:不能用if,不能用循环,不能用公式,不能直接输出结果

思路:
当n=100时
return pf[!!100](99)+100->return pf[1](99)+100----->f1(99)+100
当n=99时
return pf[!!99](98)+99----->return f1(98)+99
当n=98时
return pf[!!98](97)+98----->return f1(97)+98
......
当n=0时
return pf[!!0](-1)+0------>return f0(-1)+0//结果是0

int f0(int n)
{
	return 0;
}
int f1(int n)
{
	static int(*pf[])(int) = { f0,f1 };//pf[0]=f0 fp[1]=f1
	return pf[!!n](n - 1) + n;//递归,相当于判断
}

int main()
{
	cout << f1(100) << endl;//5050
}

如有错误,敬请指正。

您的收藏与点赞都是对我最大的鼓励和支持!

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Sweep-

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值