Jon*_*ott 6 complexity-theory functional-programming
我很好奇函数式语言(一般来说)与大型程序的C#和Java等"传统"语言的比较.与使用非功能性语言相比,程序流程是否难以更快地遵循?使用函数式语言编写大型软件项目时是否还有其他问题需要考虑?
谢谢!
Jon*_*eet 14
功能编程旨在通过将每个操作与其他操作隔离来降低大型系统的复杂性.当你编程没有副作用时,你知道你可以单独看每个函数 - 是的,理解一个函数也可能涉及理解其他函数,但至少你知道它不会干扰其他一些系统状态别处.
当然,这是假设完全纯粹的函数式编程 - 当然并非总是如此.您也可以以功能性方式使用更多传统语言,尽可能避免副作用.但原则很重要:避免副作用导致更易于维护,可理解和可测试的代码.
与使用非功能性语言相比,程序流程是否难以更快地遵循?
"程序流程"可能是分析大型功能程序的错误概念.控制流可以变成巴洛克式,因为有更高阶的函数,但这些通常很容易理解,因为很少有任何共享的可变状态需要担心,所以你可以只考虑参数和结果.当然,我的经验是,我发现遵循一个积极的功能程序比一个积极的面向对象程序更容易,其中部分实现被涂抹在许多类上.而且我发现使用高阶函数编写的程序比使用动态调度更容易.我还观察到,我的学生,作为一个整体,更能代表程序员,在继承和动态调度方面都存在困难.它们与高阶函数没有类似的困难.
使用函数式语言编写大型软件项目时是否还有其他问题需要考虑?
关键是一个好的模块系统.这是一些评论.
我所知道的最强大的模块系统是由Matthew Flatt和Matthias Felleisen设计的PLT Scheme单元系统.不幸的是,这个非常强大的系统缺少静态类型,我发现它对编程非常有帮助.
下一个最强大的系统是标准ML模块系统.不幸的是,标准ML虽然很有表现力,但也允许很多有问题的结构,所以业余爱好者很容易弄得一团糟.此外,许多程序员发现很难有效地使用标准ML模块.
Objective Caml模块系统非常相似,但有一些差异可以缓解标准ML的最严重过度.这些语言实际上非常相似,但Objective Caml的风格和习语使得初学者编写疯狂程序的可能性大大降低.
用于功能语言的最不强大/富有表现力的模块系统是Haskell模块系统.该系统存在严重缺陷,即没有明确的接口,因此丢失了模块的大部分认知益处.另一个令人遗憾的结果是,虽然Haskell模块系统为用户提供了一个分层名称空间,但是import qualified通常不赞成使用这个名称空间(如果你是一个内部人员),并且许多Haskell程序员编写代码就好像所有东西都在一个大的,平面名称空间 这种做法相当于放弃了模块的另一个重大好处.
如果我必须用功能语言编写一个大系统并且必须确保其他人理解它,我可能会选择标准ML,并且我会为模块系统的使用建立非常严格的编程约定.(例如,在任何地方都有明确的签名,:>在open任何地方都没有使用任何地方.)对我来说,标准ML核心语言的简单性(与OCaml相比)和标准ML基础库的功能性更强(相比之下)使用OCaml)比OCaml模块系统的优越方面更有价值.
我只做了一个非常大的Haskell程序,虽然我发现(并继续发现)在Haskell工作非常愉快,但我真的很想念没有明确的签名.
功能语言能否很好地应对复杂性?
有些人.我发现ML模块和模块类型(标准ML和Objective Caml)都是非常有用的工具,用于管理复杂性,理解复杂性,以及在大型程序的不同部分之间放置不可破坏的防火墙.我对Haskell的经验不足
最后说明:这些并不是真正的新问题.将系统分解为具有由编译器检查的单独接口的模块已成为Ada,C,C++,CLU,Modula-3中的问题,并且我确信许多其他语言.标准ML或Caml等系统的主要好处是可以获得明确的签名和模块化类型检查(C++社区目前正在围绕模板和概念进行讨论).我怀疑这些问题是永恒的,对任何大型系统都很重要,无论实施语言如何.