聊一下c++中的函数指针

最近在学习c++,想一边学习一边做笔记。使用博客来做笔记好像也挺大材小用的,没办法,也在培养写博客的习惯,就随便写一些吧。那么,就来说一下我在学习c++函数指针时的想法。

说起函数指针,隐约记得大一上c语言这门课有学,然而那时自己愚钝,就是理解不了(或许那时理解了,却忘了)。现在重新学起,感觉没那么吃力了,毕竟有学习了其它语言的积累。

那么,什么是函数指针?在我理解,就是指向函数的指针。有了这种指针,那么可以把函数进行传递。如果没有指针,一个函数就只能被调用。把函数进行传递,可以有什么作用?下面看一个例子。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
#include <iostream>
double add(double, double);
double sub(double, double);
double operation(double (*pf)(double, double), double, double);
int main(int argc, char const *argv[]) {
/* code */
using namespace std;
double a = 1.4;
double b = 1.5;
cout << "ensure the operator is:";
char op = getchar();
double (*opf)(double, double);//声明一个函数指针变量,指向的函数结构是有两个double型参数,并且返回double类型的值
switch (op) {
case '+':
opf = add;
break;
case '-':
opf = sub;
break;
}
cout << "the result is :" << operation(opf, a, b) << endl;
return 0;
}
double add(double a, double b) {
return a + b;
}
double sub(double a, double b) {
return a - b;
}
double operation(double (*pf)(double, double), double a, double b) {
return pf(a, b);
}

这段程序的目的是接收一个”+”或”-“号字符,然后决定对两个变量进行加法或减法运算,最后输出计算结果。

首先定义两个函数addsub,分别用来进行加法和减法运算。然后通过输入的字符来判断,用一个函数指针类型变量opf指向对应的函数(也可以说是函数的地址赋给这个变量)。最后调用opf来进行运算。

现在可能看不出函数指针有什么优点。但假如运算的种类多了,有了乘除,或者其它符合double ...(double, double)结构的函数。如果不用函数指针,就必须在每个case语句中调用方法,无疑有了重复代码。所以有了函数指针,编程会变得灵活(肯定也还有其它高级的用法)。

相似的Javascript

当我知道函数指针的基本使用时,脑海中马上浮现出Javascript中也有类似的使用场景。因为Javascript中函数是一种对象,可以赋值给任意变量。也就是说,Javascript中变量可以指向函数。先看看如何用Javascript实现上面c++的代码。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
<html>
<head>
<title>begin</title>
</head>
<body>
<p>ensure the operator is:</p>
<input id="operator" width="100px" />
<button id="btn" onclick="onClick()">calc</button>
<p id="result-output"></p>
</body>
<script type="text/javascript">
function add(a, b) {
return a + b;
}
function sub(a, b) {
return a - b;
}
function operation(func, a, b) {
return func(a, b);
}
function onClick() {
var a = 1.4, b = 1.5;
var input = document.getElementById('operator');
var opf;
switch (input.value) {
case '+':
opf = add;
break;
case '-':
opf = sub;
break;
default:
}
document.getElementById('result-output').innerHTML = 'the result is :' + operation(opf, a, b);
}
</script>
</html

相似度是不是很高。唯一的区别就是在javascript中,变量是弱类型的,不用声明它是指向函数对象的变量。

所以通过类比,我更容易理解函数指针了。就是一个变量来引用函数,但是这个变量是具体函数的类型的。什么叫具体函数的类型?一个函数的结构是怎样的?看看函数原型的定义:返回值类型+函数名+参数类型。函数名是具体的,其它两部分是类型。也就是说,只有“返回值类型+参数类型”才能把函数归纳起来成为类型。像上面的例子:

double add(double, double);

double sub(double, double);

函数addsub的类型就是返回值为double类型,参数为两个double类型。后面就定义了这样一个类型的函数指针:double (*opf)(double, double)。看到这个声明,可以这样理解:opf变量的类型是函数指针,它只能指向返回值为double类型的,有两个double类型参数的函数。

Comments