思考并回答以下问题:
到目前为止,您已经了解了什么是函数式编程以及如何使用它来解决一些常见的编程问题的基础知识。在本章中,您将了解如何将功能代码放入现有或新应用程序中。具体来说,您将看到以下内容:
- 如何构造函数式应用程序以及使其充分发挥功能
- 如何以及何时混合和匹配范式,例如功能和面向对象的编程
PHP范式的历史
函数的引用透明性(referential transparency)
- 基础
初学程序设计时,比较容易混淆的两个概念是数学函数(math function)和程序中使用的函数。
在数学函数中 y=f(x),一个输入值有固定的输出值。例如,无论计算多少次,sinπ 的结果总是 0。如果 f(x)=x/2,那么 f(10) 无论计算 100 次还是 1000 次,其结果都是 5.
程序设计中的函数却不具备这种稳定的特性,因为函数的执行不仅依赖于输入值,而且会受到全局变量,输入文件,类的成员变量等诸多因素的影响。如下:1
2
3
4int counter = 0;
int count(){
return ++counter;
}
此函数输入没有输入值,但每次都返回不同的结果。当然,就像数学函数那样,程序中函数还可以设计成“对同一输入值每次都返回相同结果”的形式。
函数的返回值只依赖于其输入值,这种特性就称为引用透明性(referential transparency)
- 动态规划的缓存
显然,动态规划所使用的制表法(也即缓存)只能应用于具有引用透明性的函数。如果外在因素使相同输入值返回不同结果值,则不能缓存。
也即缓存对应的 map,实现的是同一个输入(key),同一个输出(value),而不可能出现同一个输入,可以得到不同的输出,也即输出结果的不确定性。
使事情简单明了的最佳方法是将您的代码分为功能和非功能代码块。 一个明显的安排是用功能代码编写业务逻辑,高性能算法等,并将其夹在不纯的OO或过程代码之间以处理输入和输出,如图7-1所示。
通过这样的安排,您可以使用干净的功能代码块来进行推理和测试,并且当问题确实发生时,更容易找出它们可能位于的位置。 当您面对使用功能性技术更新现有代码库时,一种好的方法是首先确定适合图7-1中间部分的代码部分,然后优先确定它们的优先级。
1 |
|
1 |
|
1 |
|
1 |
|
1 |
|
1 |
|
1 |
|
1 |
|