Scheme与Haskell进行函数式编程简介?


36

我对使用C和C#编程感到满意,并且将来会探索C ++。我可能对将函数式编程作为一种不同的编程范例进行研究感兴趣。我这样做很有趣,我的工作不涉及计算机编程,并且在大学的计算机科学课程中就很早就开始使用函数式编程,这在某种程度上受到了启发。Lambda微积分当然超出了我的数学能力,但是我认为我可以处理函数式编程。

Haskell或Scheme中的哪一个可以很好地介绍函数式编程?我将emacs用作文本编辑器,并希望将来能够更轻松地对其进行配置,这需要学习Emacs Lisp。但是,我的理解是Emacs Lisp与Scheme完全不同,并且在功能性方面也更具程序性。

如果我追求Scheme,我可能会使用已经购买的“ The Little Schemer”书(我有限的翻阅对我来说似乎有些不可思议)。或者,如果我追求Haskell,可以使用“向您了解Haskell的伟大成就”。我还将在第9频道上观看Erik Meijer博士的Haskell简介视频。

任何建议,反馈或意见表示赞赏。

谢谢。

PS BTW由于我拥有用于​​C#开发的Visual Studio 2010,因此我也可以使用F#,但是我认为这不是我选择语言的主要标准。


3
别忘了Real World Haskell
替代

15
次要方面的评论:lambda演算是一个非常简单的系统;有趣的是,它不是很复杂,而是相反。您可以在这样一个简单的系统中表达您想要的一切。从编程语言开始;现在扔掉一切,除了变量引用,函数定义和函数调用。瞧!Lambda演算。


9
我可以在五分钟内教你lambda演算。现在,了解您刚刚学到的结果将花费一生。:)

5
我之所以选择Haskell而不是Scheme,主要是因为它没有太多的括号!
乔伊·亚当斯

Answers:


27

我会推荐OCaml。

以我个人的观点,现代功能编程的主要基础是高阶函数,静态类型系统以及代数数据类型和模式匹配。

在方案,ML和Haskell之间,我会选择ML,因为我认为它与该定义最相关。Scheme没有静态类型化(有Typed Racket,但不是针对计划初学者的),Haskell还有太多其他东西(monad,懒惰的评估...),尽管有趣,但可能会将注意力从重要基础上转移开。

SML和OCaml同样有趣。我更习惯OCaml,它具有一种“实用”的感觉,这是很好的感觉(但是,如果您真的希望“实用”以免失去灵魂,可以选择F#)。

Scheme和Haskell也是非常有趣的语言。方案对宏的强调很有趣,但与功能编程没有直接关系(这是世界上您绝对应该尝试的另一件事,以及逻辑编程,基于堆栈的语言和面向功能的E)。

Haskell绝对是一门很棒的语言,我认为,这是有抱负的函数式编程大师的必修课。但是,由于OCaml和Haskell的核心语言非常相似(除了对初学者来说分散注意力的惰性评估),一旦了解了OCaml的基础知识,就很容易学习Haskell。或者,您可以专注于奇怪的东西,而不必同时吸收基础知识。

同样,一旦您了解了OCaml,可能还了解了Haskell,并且仍然想了解更多信息,则应该看一下Coq或Agda。但是很少有人会推荐Coq或Agda首次介绍函数式编程...

明确地说:我认为,先学习OCaml(或SML),然后再进行Haskell,将使您像直接学习Haskell一样,成为一个好的函数程序员,但是更容易(或减轻痛苦)。
此外,OCaml中和Haskell都有好东西区分它们,它们也同样吸引了解的高级功能两者。仅学习Haskell在这方面较差(尽管您当然可以在Haskell之后学习OCaml;我认为这样做不合逻辑,会使您更加沮丧)。

为了学习OCaml,我将推荐Jason Hickey的书稿(PDF)

¹ 这个定义是有争议的。一些Scheme的人会声称静态类型与函数式编程无关。一些Haskell人会声称他们对纯净度的定义(“ Haskell做了什么,但没有更多”)是成为功能语言的必要条件。我同意不同意。


3
感谢您将我推向OCaml,是的,我会冒险冒险探索F#。我确实为Linux,Mac OS X和Windows(主要是前者)进行开发,但FSI确实适用于我已经使用的所有三个平台(在Linux和Mac OS X上运行mono)。Microsoft的全部功能都在一种功能性编程语言(尽管是一种“不纯正的”)背后,这一事实应该受到欢迎,而不是受到功能性编程爱好者的谴责。
haziz 2011年

SML已死,存在用ocaml编写
Coq

1
ML +1;比Haskell更清楚。
m3th0dman 2012年

我还发现学习SML或OCaml,然后学习Haskell(+1)是一个好主意。掌握了这些语言之后,选择另一种语言(例如Scala)非常容易。另外,可以看一下Scheme,Common Lisp和Clojure(按此顺序),以感受动态语言。
Giorgio

@haziz:即使他们创造良好的软件,微软(或者,就此而言,甲骨文等)仍然是一个垄断者,与所有涉及的不良行为,如客户锁定,不兼容的格式,不兼容的实现,等等
乔治·

26

如果您对函数式编程中的更高级概念感兴趣,请使用Haskell。有一个适当的类型系统和严格的禁止突变。尽管如此,Haskell还是不适合胆小的人。

如果您只想介绍功能设计,请使用Scheme。语法更容易学习和阅读。它的确允许进行过程编程,但只是要管教自己不要使用!名称结尾的任何过程。

使用Scheme,您还可以阅读《计算机程序结构和解释》,这是编程范例的最佳入门指南。麻省理工伯克利都有关于这本书的讲座。


4
“语法更容易学习和阅读”是非常主观的。

6
@luqui:是的。也许“常规”是一个更好的词。没有反引号,中缀,优先级或关联性问题-只是括号,很多地狱,愚蠢的括号。
Hoa Long Tam

17

正确的答案当然是两者!因此,这只是首先要处理哪种语言的问题。我的情况和你一样。我真的非常喜欢《小策划者》。读完之后,您一定会理解函数式编程的基本结构(并有放置果冻的地方!)

我大约有四分之一的兴趣为您学习Haskell。我也很享受这一点,但是这两本书没有什么不同。向您学习Haskell具有一种非常传统的方法来教授特定语言。显然,Little Schemer特定于Scheme,但更多地是在讲授函数式编程的基础知识,而不是Scheme的语言。

我绝对建议从The Little Schemer开始。它不太实用,但更基础。


17

关于函数式编程,我的两分钱不是要挂在一种特定的语言上,而是要学习函数式编程的关键概念。我首先投入了一个项目,我的老板坚持要在APL中完成所有开发工作,从而学习了函数式编程。APL是一种功能性的阵列处理语言,并且与LISP,Haskell或任何其他主流编程语言都相距甚远。真正的收获是,当我发现我“摸索”函数式编程范例并从心中学会了如何将问题自动神奇地分解为函数式程序时,我真的不再被Haskell等其他函数式语言的惯用语言所吓倒, OCaml,Scheme,Scala和Clojure。一世'

如果要选择第一种功能语言,则可能会选择Haskell或Steel Bank Common Lisp(SBCL)。对于Haskell,我将阅读“ 了解您的Haskell ...”,“ 现实世界中的Haskell”“ Haskell逻辑,数学和编程之路”以及“功能算法设计的明珠”。对于CL,我将阅读Lisp之地人工智能编程范例,以及(如果您真的很顽固的话)Lake over Lambda。您可以将所有这些书籍混在一起使用,以获得对实用函数式编程方法和概念的广泛概述。

我还将考虑学习Clojure和Scala,因为它们本身就是非常好的语言,而且表达能力很强(尽管FP纯粹主义者可能会说)。


6

我同意“两者都学习”的观点,但是到目前为止还没有提到其他几点。首先,如果您是函数式编程的新手,并且选择了Haskell,那么除了FP之外,您还需要面对其他一些新事物:您需要学习如何生活在一个懒惰的环境中,这需要花费大量的精力,并且您需要处理“真实”类型的系统,该系统可能与您在C或C#中使用的系统相去甚远。

Scheme OTOH确实具有外来的语法,但是没有学习静态类型的系统,而且它是一种严格的语言,因此人们对它更加熟悉。此外,Scheme的实现往往具有很好的延展性-例如,Racket将其实现到了极致,并提供了一个惰性变体和一个静态类型化的变体。这意味着您可以从“简单”的东西开始,掌握使用功能性语言的习惯,然后再发展自己,使用类型化的变体和懒惰的变体。现在,它们应该会更容易,因为您一次只能处理一项功能。要明确的是,这些概念将会变得足够新,以至于语法问题将变得很小并且几乎无关紧要。换句话说,一旦开始使用新概念,您将非常忙,以致语法将消失。(而且,如果您真的很在乎语法,那么我个人认为Haskell的语法非常优雅-但这是因为它与您的平均C / C#/ C ++语法也相差很远。)

综上所述,我认为F#还有一个好处-您说这是附带条件,但是当您学习FP时,很快就会想使用所有这些好东西。使用F#意味着您可以做更多的“实际”事情,因为解决日常工作中遇到的同类问题很容易。理想情况下,您将了解到使用C#而不是使用C#的优势-并在某些项目中使用它。因此,虽然您不仅仅因为更容易访问而选择F#是正确的,但应该考虑一下它,因为没有什么比实际使用中更好的了这些新概念。相比之下,如果您使用Scheme或Haskell并将其视为玩具语言(即使您知道有人在实际应用中使用它),则您永远不会对整个FP事情太当真。[但是YMMV,它主要是基于主观观察,并且每个人之间的差异可能很大。]


6

为何ML不是您的选择之一?有大量的入门资料,包括书籍和课程讲义。如果您喜欢The Little Schemer,您可能还会喜欢The Little MLer。最后,您可以稍后轻松地过渡到F#。(并不是说我要敲Haskell或Scheme-理想情况是要同时学习全部三个)。

另外,对Emacs Lisp的警告。我认为Haskell或ML都不会为您做好准备。像Scheme这样的Lispy语言会有所帮助,但仍然存在主要差异,例如。动态范围变量。从本质上讲,Emacs扩展往往比功能更重要-它们都是关于更改编辑器状态的。


感谢您推动我学习ML / OCaml,是的,我会“冒风险”并探索F#。我确实为Linux,Mac OS X和Windows(主要是前者)进行开发,但FSI确实适用于我已经使用的所有三个平台(在Linux和Mac OS X上运行mono)。Microsoft的全部功能都在一种功能性编程语言(尽管是一种“不纯正的”)背后,这一事实应该受到欢迎,而不是受到功能性编程爱好者的谴责。
haziz 2011年

顺便说一句,我确实从亚马逊订购了The Little MLer,并且已经收到它并开始我的旅程。我也刚刚将Learning F#添加到我的库中。似乎是更主流的教学指南,我将以此为补充《 Little MLer》。
haziz 2011年

6

在48小时内为自己编写一个计划(以Haskell为准)

我真的推荐这个。您将通过一个真实而有趣的问题学习Haskell,并通过与您构建的解释器一起玩来学习方案的最佳课程。如果您走这条路,请保持一些Haskell良好的介绍。如果您有问题要解决,您将更好地理解它们。


我实际上是使用此Wiki / pdf来学习Haskell的,并掌握了我的OCaml技能(通过将惯用的Haskell转换为OCaml)。如果有人可以接受此材料并将其“分叉”成几种功能语言,那将非常酷。可能是相当不错的功能语言大战的基础!
Marc

1
这样做的主要问题是它引入了parsec而没有引入monad。
选项

@alternative parsec具有Monadic接口,但也具有Applicative接口,更不用说许多其他功能了。这不是不合理的单子泛化之前引进秒差距
菲利普JF

4

我会和Haskell一起去。在方案中,您可能会被推到做程序性的东西,它的类型系统是几乎没有帮助的有Haskell的,这是伟大的初学者,因为它几乎会检查你的代码在编译时是正确的。


3
“相当多的检查代码是否正确”是非常错误的。没有类型系统可以做到这一点。(除非您的类型系统是一个真正的定理证明者。)
Eli Barzilay

4
@Eli,您使用过Haskell吗?虽然从理论上讲该声明显然是错误的,但实际上,至少与我使用的其他每种语言相比,我发现它都是非常准确的。就是说,我实际上不同意这对初学者来说是不错的选择。当我学习绳索时,我宁愿明确地看到我的代码做错了什么,而不是让编译器对我大喊大叫这是错误的,并且在我什至不知道错误消息正在使用的词汇时不得不与之抗争。

1
@Eli“差不多”是这里的关键术语。在Haskell中,您花了更多时间思考如何实现它,然后实现就很容易了。然后您对它进行类型检查,以确保您的地图,折叠等完好无损。
可替代

@Eli Barzilay:Haskell的类型系统肯定看起来非常接近定理证明者。它无疑创造了一个环境,定理证明似乎比其他工具更普遍。(并不是说我是在暗示因果关系。)
greyfade 2011年

@luqui-是的,我用过;不,无论从实践还是从理论上讲,这仍然是错误的说法。但是,这并不是Haskell独有的。
Eli Barzilay

1

我认为很容易陷入有关语言的辩论中而错过了重点。对于只想了解FP的人来说,Ocaml / ML / Scheme / Haskell之间的差异并不比您对用来学习FP的材料(书籍,视频,工具)的舒适程度重要一半。而且,无论您是否有朋友来帮助您学习某些语言,都比其他任何事情都重要。


0

如果不是纯语言,则最好使用命令式语言,Haskell也是如此。


0

在收到的关于您问题的答案之一中,我发现此链接非常有趣,因为它使您对Haskell和Scheme有所了解。

除了这个漂亮的链接,这是我对你的问题的看法。

如果您来自命令式编程的背景,则可能会花很多精力来学习函数式编程。我将确保学习经验不会是空的。那就是您可以将其应用于当前或下一份工作,或者以其他方式为您提供帮助。

有很多不错的语言。斯卡拉(Scala)人民,克劳瑞(Clojure)和CL人民都会赞美他们的语言。甚至Pythonista使用者也声称自己懒惰。回答您的其他人建议ML。撰写《 Clojure in Action》的Amit Rathore甚至可能建议您学习Haskell。

您提到了Windows和F#。这对您目前的职位有帮助吗?我对F#一无所知。功能是否足够?我之所以这么问,是因为IMHO Python具有功能构造,但它与Clojure中的编程不同。

总而言之,学习一种“真正”功能的功能语言,这样做对您的情况最有意义。


-2

从相对初学者的角度来看,如果您决定使用Scheme,我建议不要从SICP开始,除非您的数学已经相当成熟。这本书和视频充满了微妙之处,对于刚开始的人根本不直观。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.