Scala 为什么;“从文件中读取”;这不是纯函数吗?
在《Scala中的函数编程》一书中,给出了几个“副作用”的例子,其中之一是:Scala 为什么;“从文件中读取”;这不是纯函数吗?,scala,functional-programming,Scala,Functional Programming,在《Scala中的函数编程》一书中,给出了几个“副作用”的例子,其中之一是: 读取或写入文件 我可以理解“写入文件”并不纯粹,因为它改变了环境。但为什么“读取文件”不纯粹?这不会改变任何事情 参见我的示例: val readFile: File => String = file => readingTheContentFromFile(file) 对于相同的输入,纯函数总是返回相同的值。否则,它将基于副作用(如更改文件)。 如果从文件中读取,结果可能会更改,而函数的参数不会更改
- 读取或写入文件
val readFile: File => String = file => readingTheContentFromFile(file)
对于相同的输入,纯函数总是返回相同的值。否则,它将基于副作用(如更改文件)。 如果从文件中读取,结果可能会更改,而函数的参数不会更改
相关概念是“参考透明度”。这意味着您可以用函数返回的结果替换函数调用和给定的参数集。因此,从文件中读取不是引用透明的 在函数式编程中,函数是
也就是说,不是实际读取文件,而是获取“文件内容”作为参数,而不是实际写入文件,而是返回“文件输出”作为值。在大多数实用语言中,这似乎是一个思考练习。如果函数是纯函数,那么执行它总是安全的,即可以替换以下伪代码
do {
x = readFile "file.txt"
writeFile "file.txt" "Goodbye"
return (x + readFile "file.txt")
}
与
你会得到同样的结果。但很明显,由于在第一个示例中,对
writeFile
的调用出现在对readFile
的两个调用之间,因此这不是一个安全的转换,因此函数不是纯函数。如果对于相同的输入参数,函数给出相同的结果,则函数是纯函数,因此:
- 函数
不是纯粹的,因为如果给定相同的write(file)
,它可能导致成功或失败文件
- 函数
不是纯粹的函数,因为给定相同的read(file)
,它每次都可能返回不同的数据或失败文件
write(file)
或read(file)
不能被其结果替换,因为下次进行相同调用时,它可能会产生不同的结果
纯函数的美妙之处在于,如果它们现在成功了,那么您可以确信,如果它们和它们调用的函数此后没有改变,它们将继续成功
请注意,纯度与改变或不改变环境无关,因为:
- 每个函数在内部读取和写入计算机内存,并消耗能量,因此每个函数都会改变环境
- 如果读取和写入同一个文件总是返回相同的结果,那么这些函数将是纯函数,尽管它们会接触环境
do {
x = readFile "file.txt"
writeFile "file.txt" "Goodbye"
return (x + x)
}