Functional programming 在纯函数语言中,数据(字符串、整数、浮点..)也只是函数吗?

Functional programming 在纯函数语言中,数据(字符串、整数、浮点..)也只是函数吗?,functional-programming,lambda-calculus,purely-functional,Functional Programming,Lambda Calculus,Purely Functional,我在考虑像Ruby这样的纯面向对象语言,其中所有东西,包括数字、int、float和字符串本身都是对象。纯函数式语言也是这样吗?例如,在Haskell中,数字和字符串也是函数吗 我知道Haskell是基于lambda演算的,它将所有东西,包括数据和操作,都表示为函数。在我看来,“纯函数语言”将把所有东西都建模为一个函数是合乎逻辑的,并且符合这样一个定义,即一个函数总是返回具有相同输入的相同输出,并且没有状态 从理论上考虑这个问题是可以的,但是 就像在Ruby中,并非所有东西都是对象(例如参数列表

我在考虑像Ruby这样的纯面向对象语言,其中所有东西,包括数字、int、float和字符串本身都是对象。纯函数式语言也是这样吗?例如,在Haskell中,数字和字符串也是函数吗


我知道Haskell是基于lambda演算的,它将所有东西,包括数据和操作,都表示为函数。在我看来,“纯函数语言”将把所有东西都建模为一个函数是合乎逻辑的,并且符合这样一个定义,即一个函数总是返回具有相同输入的相同输出,并且没有状态

从理论上考虑这个问题是可以的,但是

就像在Ruby中,并非所有东西都是对象(例如参数列表),Haskell中也并非所有东西都是函数


更多参考,请查看这篇整洁的帖子:

@wrhall给出了一个很好的答案。然而,您在某种程度上是正确的,在纯lambda演算中,一切都是函数是一致的,并且语言是图灵完备的(能够表达Haskell等的任何纯计算)

这给了你一些非常奇怪的东西,因为你能对任何东西做的唯一一件事就是把它应用到其他东西上。你什么时候能观察到什么?你有一些值
f
,你想知道一些关于它的事情,你唯一的选择是应用它一些值
x
来获得
fx
,这是另一个函数,唯一的选择是将它应用到另一个值
y
,来获得
fx
,等等

我经常将纯lambda演算解释为讨论非函数的事物上的转换,而这些事物只能表达函数本身。也就是说,我可以创建一个函数(带有一点递归和let的haskell语法):

在这里,我表达了计算
2+2
,而不需要知道有非函数之类的东西。我只是把我需要的作为我定义的函数的参数,这些参数的值可以是church编码,也可以是“实数”(不管这意味着什么)——我的定义不在乎

你也可以对哈斯克尔有同样的想法。没有特别的理由认为有些东西不是函数,也没有特别的理由认为一切都是函数。但是Haskell的类型系统至少阻止你对一个数字应用一个参数(现在想从Integer开始的任何人都需要保持沉默!)。在上面的解释中,这是因为数字不一定是作为函数建模的,所以您不一定可以对它们应用参数


如果现在还不清楚的话,那么这个完整的答案在某种程度上是一个技术/哲学上的离题,对你的问题的简单回答是“不,不是所有的东西都是函数语言中的函数”。函数是可以应用参数的对象,仅此而已。

关于这个问题,有一个非常不同的角度:Haskell中的各种数据都可以用函数表示,使用一种称为的技术。这是控制反转的一种形式:不是将数据传递给使用它的函数,而是将数据隐藏在一组闭包中,要使用它,需要传递回调来描述如何处理这些数据

例如,任何使用列表的程序都可以转换为使用函数而不是列表的程序:

——|列表对应于此类型的函数:
键入a r=(a->r->r)--^如何处理cons单元格
->r--^如何处理空列表
->r--^处理列表的结果
listToCPS::[a]->列出一个r
listToCPS xs=\f z->foldr f z xs
该函数以一个具体的列表作为起点,但这不是必需的。您可以从纯函数中构建
ChurchList
函数:

——|空的“教堂名单”。
无::丘吉尔
nil=\f z->z
--|在“教堂名单”前面添加一个元素。
缺点:a->ChurchList a r->ChurchList a r
cons x xs=\f z->f z(xs f z)
文件夹列表::(a->r->r)->r->教堂列表a->r
文件夹列表f z xs=xs f z
地图丘吉尔列表::(a->b)->丘吉尔列表a r->丘吉尔列表b r
mapChurchList f=foldChurchList步骤nil
其中步骤x=cons(f x)
过滤器目录列表::(a->Bool)->教堂列表a r->教堂列表a r
filterChurchList pred=折叠churchlist步骤nil
其中步骤x xs=如果pred x那么cons x xs else xs
最后一个函数使用
Bool
,但我们当然也可以用函数替换
Bool

——|布尔可以表示为在两个函数之间进行选择的函数
--给定备选方案。
类型:r=r->r->r
对,错::丘吉尔
真a=a
假b=b
过滤器目录'::(a->丘吉尔布尔r)->丘吉尔列表a r->丘吉尔列表a r
filterChurchList'pred=foldChurchList步骤nil
其中,步骤x xs=pred x(cons x xs)xs
这种类型的转换基本上可以对任何类型进行,因此在理论上,可以去掉Haskell中的所有“值”类型,只保留
()
类型、
(->)
IO
类型构造函数、
返回
>=
for
IO
,以及一组合适的
IO
原语。这显然是不切实际的,而且效果会更差(试着写一篇文章试试看)。

在“纯功能”中的“纯”指的是“无副作用”的纯。当人们谈论“纯面向对象语言”时,它与“纯”的含义几乎没有关系,而“纯面向对象语言”只是指该语言纯粹(仅)在对象中进行操作。
purePlus = \zero succ natCase -> 
   let plus = \m n -> natCase m n (\m' -> plus m' n)
   in plus (succ (succ zero)) (succ (succ zero))