第35课 函数对象分析

客户需求:

需求的第二条比较难以实现,例如第一次调用返回1,第二次返回1,第三次返回2,第四次返回3。

也就是说fib函数是带状态的,每次返回的值都不同。

我们以前接触过的函数大多数都是无状态的。

简单的解决方案就是使用全局变量记录状态,而程序开发中全局变量又是不被推荐使用的,那么还有什么其它的方法吗?

除了全局变量,还可以使用静态局部变量。

示例程序:

每一次调用都返回不同的值,初步满足了用户需求。

可重复使用:

第二个for循环依旧可以打印。

存在的问题:

如果我们调用100次之后又想从第一项开始就没有办法了。

我们将静态变量改为全局变量,再次更改程序:

当需要从第一项开始打印的时候只需要重置全局变量的值。

而这个方案并不完美,用户要的只是一个函数,而我们现在将重置全局变量的工作也交给了用户,这是不符合要求的。

最终解决方案:

 怎么具体完成这项工作呢,那就是操作符重载了。

()操作符是编译器内置的操作符,它的地位和数组访问操作符[]是一致的。

程序如下:

 1 #include <iostream>
 2 #include <string>
 3 
 4 using namespace std;
 5 
 6 class Fib
 7 {
 8     int a0;
 9     int a1;
10 public:
11     Fib()
12     {
13         a0 = 0;
14         a1 = 1;
15     }
16     
17     Fib(int n)
18     {
19         a0 = 0;
20         a1 = 1;
21         
22         for(int i=2; i<=n; i++)
23         {
24             int t = a1;
25             
26             a1 = a0 + a1;
27             a0 = t;
28         }
29     }
30     
31     int operator () ()
32     {
33         int ret = a1;
34     
35         a1 = a0 + a1;
36         a0 = ret;
37         
38         return ret;
39     }
40 };
41 
42 int main()
43 {
44     Fib fib;
45     
46     for(int i=0; i<10; i++)
47     {
48         cout << fib() << endl;
49     }
50     
51     cout << endl;
52     
53     for(int i=0; i<5; i++)
54     {
55         cout << fib() << endl;
56     }
57     
58     cout << endl;
59     
60     Fib fib2(10);
61     
62     for(int i=0; i<5; i++)
63     {
64         cout << fib2() << endl;
65     }
66     
67     return 0;
68 }

第31行就是()操作符重载了。重载了这个操作符之后,我们生成的类对象就可以当做函数来调用了。

如果想从第一项开始输出,只需要重新定义一个对象。

还可以指定从第几项开始返回,只需要重新定义一个构造函数。

运行结果如下:

小结:

 在C++的工程中尽量少用原生指针,我们使用string对象取代字符串,对于数组我们可以使用数组对象取代,对于函数指针就可以用函数对象取代。

原文地址:https://www.cnblogs.com/wanmeishenghuo/p/9572902.html