我曾经认为变量是数据和函数作为数据映射,它们在一般意义上是不同的东西。但是,在阅读某些语言标准(即Haskell)时,我发现该标准似乎将它们组合在一起(参见2.4,和10.5,以及this question)。
所以,我有一些关于变量和函数的问题(除问题标题外):
编辑:
摘要
在阅读完所有答案后(他们真的很棒),我意识到我的怀疑是由于“操作员”和“功能”之间的混淆:我把这两件事搞错了。 正确的理解应该是:“运算符”只是一个符号,它指的是“函数”。
请允许我借用E-Lisp Intro的解释,我发现它非常有用:
我们可以根据我们所讨论的内容阐明Lisp的另一个特征 远 - 一个重要的特征:符号,如+,本身不是指令集 为计算机进行。而是使用符号,也许是暂时的, 作为定位指令或指令集的一种方式。我们看到的是这个名字 通过它可以找到指令。人们的名字以同样的方式工作。 我可以被称为'鲍勃';但是,我不是字母'B','o','b',而是我或者是, 意识始终与特定的生命形式相关联。名字是 不是我,但它可以用来指我。
答案 0 :(得分:11)
不,函数不是变量。函数是一个值(在Haskell,Python,JavaScript,Clojure和许多其他语言中,但不是在所有语言中)。变量(或符号,标识符)可以引用或绑定到值。因此,变量/符号/标识符可以引用函数。
您的子问题:
恕我直言,是的。例如,数学中存在高阶逻辑。在数学中也存在常见的高阶函数,例如导数,积分和求和。
恕我直言,变量不是由"定义" - 价值也有类型,虽然可能在不同的意义上 - 但更多的是它们代表(代表,参考,指向)其他东西的能力。
"什么是变量?"应该被视为一个单独的问题,因为根据我的理解,准确的答案令人惊讶地复杂并植根于数学史。
更仔细地阅读你的问题,我认为这里有两个不同的问题:1)"是什么"什么? 2)不同事物之间的相似之处。因此,虽然您已经确定了变量和函数之间的相似性,但这并不意味着函数"是"变量,反之亦然。我将尝试使用Java示例来说明这一点(请耐心等待我!):假设您有一个包含两个类的Java程序Variable
和Function
,并且您想知道如何在它们之间创建继承关系。我的答案是,我不认为有一个 - 没有一个继承自另一个 - 但你不需要一个,因为你可以创建接口捕捉你感兴趣的方面,然后为这两个类实现这些接口。
答案 1 :(得分:6)
函数是一种类似于
的语法形式\ x -> E
以及一些变化。如果表达式E
的类型为b
,并且x
中对E
的所有引用都具有a
类型,那么整个表达式的类型为a -> b
相反,take
或(.)
之类的内容是变量。事实证明,在每种情况下,该变量的类型都是a -> b
形式,因此变量代表一个函数。
由于Haskell是纯粹的,我们保证用它所代表的值替换变量不会改变程序的含义。
(我暂时忽略了句法形式和价值观之间的区别 - 你可以长时间模糊这种区别而不会有太多麻烦。)
这种自由取代参考的价值观念是数学变量的典型含义 - 虽然不是反映它的最核心方式。
通常,变量是 unknown ,可能受到任何数量的限制。例如,它可以参与一个方程组,并被约束为该系统的解决方案
a = (True, a) -- invalid Haskell, but a valid concept! What is "a" here?
Haskell变量不能直接定义:变量可以参与的递归方程的种类有限制,这些是由Haskell的类型判断给出的。
但是,尽管我试图区分"典型的"数学变量和Haskell变量,两者是FAR更相似的变量"变量"在其他计算机语言中。那些可能更好的命名" mutables"或" assignables"。
最后,函数的本质是什么?如果你"有"通过变量引用或语法形式的函数,然后您可以将应用于参数。这会导致出现一种形式的变量替换。我们已经说过变量可以在引用某些变量时自由替换 - 为什么我们需要函数?
因为函数的构造产生了包含绑定变量的上下文。这些变量只在函数体内有意义,并且在应用函数并且局部气泡上下文融化回程序之前,不能采用任何实际参考。
通常,函数和变量具有复杂的相互作用。研究(打字或无类型)lambda演算就是这个。
答案 2 :(得分:-2)
如果函数的概念是返回变量,则可以假设它是调用者的变量。但我怀疑规范会将函数视为变量的子集,因为它并不能捕获函数的全部本质。