简体   繁体   English

功能编程和类型系统

[英]Functional Programming and Type Systems

I have been learning about various functional languages for some time now including Haskell, Scala and Clojure. 我一直在学习各种函数式语言,包括Haskell,Scala和Clojure。 Haskell has a very strict and well-defined static type system. Haskell有一个非常严格且定义良好的静态类型系统。 Scala is also statically typed. Scala也是静态类型的。 Clojure on the other hand, is dynamically typed. 另一方面,Clojure是动态类型的。

So my questions are 所以我的问题是

  1. What role does the type system play in a functional language? 类型系统在函数式语言中扮演什么角色?
  2. Is it necessary for a language to have a type system for it to be functional? 语言是否有必要使用类型系统才能使其正常运行?
  3. How is the "functional" level of a language related to the kind of the type system of the language? 语言的“功能”级别与语言类型系统的类型有何关联?

A language does not need to be typed to be functional - at the heart of functional programming is the lambda calculus , which comes in untyped and typed variants. 语言不需要输入功能 - 函数式编程的核心是lambda演算 ,它是无类型和类型变体。

The type system plays two roles: 类型系统扮演两个角色:

  • it provides a guarantee at compile time that a class of errors cannot occur at run-time. 它在编译时提供了一种保证,即在运行时不会发生一类错误。 The class of errors usually includes things like trying to add two strings together, or trying to apply an integer as a function. 错误类通常包括尝试将两个字符串添加到一起,或尝试将整数应用为函数。
  • it has some efficiency benefits, in that objects at runtime do not need to carry their types around, because the types have already been established at compile-time. 它具有一些效率优势,因为运行时的对象不需要携带它们的类型,因为类型已经在编译时建立。 This is known as type erasure . 这被称为类型擦除

In advanced type systems like Haskell's, the type system can provide more benefits: 在像Haskell这样的高级类型系统中,类型系统可以提供更多好处:

  • overloading: using one identifier to refer to operations on different types 重载:使用一个标识符来引用不同类型的操作
  • it allows a library to automatically choose an optimised implementation based on what type it is used at (using Type Families ) 它允许库根据其使用的类型自动选择优化的实现(使用Type Families
  • it allows powerful invariants to be proven at compile time, such as the invariant in a red-black tree (using Generalised Algebraic Datatypes ) 它允许在编译时证明强大的不变量,例如红黑树中的不变量(使用广义代数数据类型

What role does the type system play in a functional language? 类型系统在函数式语言中扮演什么角色?

To Simon Marlow's excellent answer, I would add that a type system, especially one that includes algebraic data types , makes it easier to write programs: 对于Simon Marlow的优秀答案,我想补充一个类型系统,特别是包含代数数据类型的系统 ,可以更容易地编写程序:

  • Software designs, which in object-oriented languages are sometimes expressed using UML diagrams, are very clearly expressed using types. 面向对象语言中的软件设计有时使用UML图表示,使用类型非常清楚地表达。 This clarity manifests especially when not only values have types, but also modules have types, as in Objective Caml or Standard ML. 这种清晰度尤其表现在不仅具有类型,而且模块具有类型,如在Objective Caml或Standard ML中。

  • When a person is writing code, a couple of simple heuristics make it very, very easy to write pure functions based on the types: 当一个人编写代码时,一些简单的启发式方法可以很容易地根据类型编写纯函数:

    • A value of function type can always be created with a lambda. 始终可以使用lambda创建函数类型的值。
    • A value of function type can always be consumed by applying it. 通过应用它可以始终消耗函数类型的值。
    • A value of an algebraic data type can be created by applying any of the type's constructors. 可以通过应用任何类型的构造函数来创建代数数据类型的值。
    • A value of an algebraic data type can be consumed by scrutinizing it with a case expression. 通过用case表达式仔细检查代数数据类型的值,可以消耗它。

    Based on these observations, and on the simple rule that unless there's a good reason, a function should consume each of its arguments, it's pretty easy to cut down the space of possible code you could write to a very small number of candidates. 基于这些观察结果,以及简单的规则,除非有充分的理由,函数应该使用它的每个参数,否则很容易减少可以写入极少数候选者的可能代码的空间。 For example, there just aren't that many sensible functions of type (using Haskell notation) 例如,没有那么多合理的类型函数(使用Haskell表示法)

     forall a . (a -> Bool) -> [a] -> Bool 

    The art of using types to create code is called type-directed programming. 使用类型创建代码的技术称为类型导向编程。 When it works well, you hear functional programmers say things like "once we got the types right, the code practically wrote itself." 当它运行良好时,你会听到功能程序员说“一旦我们得到了正确的类型,代码实际上就自己编写了”。 Since the types are usually much smaller than the code, this is a big win. 由于类型通常比代码小得多,这是一个很大的胜利。

  1. Same as in any programming language: it helps you to avoid/find errors in your code. 与任何编程语言相同:它可以帮助您避免/查找代码中的错误。 In case of static typing a good type system prevents programs with certain types of errors from compiling. 在静态类型的情况下,良好类型系统可防止编译具有某些类型错误的程序。
  2. No. The untyped lambda calculus is what you could call the prototype of functional programming languages and it is, as the name suggests, entirely untyped. 没有。 无类型的lambda演算是你可以称之为函数式编程语言的原型,顾名思义,它完全是无类型的。
  3. In a functional language (as well as any other language where a function can be used as a value) the type system needs to know what the type of a function is. 在函数式语言(以及函数可用作值的任何其他语言)中,类型系统需要知道函数的类型。 Other than that there is nothing special about type systems for functional languages. 除此之外,功能语言的类型系统没有什么特别之处。

    In a purely functional language you need to abstract side-effects, so you'd want the type system to somehow be able to support that. 在纯函数式语言中,您需要抽象副作用,因此您希望类型系统能够以某种方式支持它。 For example if you want to have a world type like in Clean, you'd want the type system to support uniqueness types to ensure proper usage. 例如,如果您希望拥有类似于Clean的世界类型,则您希望类型系统支持唯一性类型以确保正确使用。

    If you want to have an IO monad like in haskell, you'd need an IO type (though a monad typeclass like in haskell is not required to have an IO monad, so you don't need a type system, which supports that). 如果你想在haskell中有一个IO monad,你需要一个IO类型(虽然像haskell这样的monad类型类不需要有一个IO monad,所以你不需要一个支持它的类型系统) 。

1: Same as any other, it stops you from doing operations that are either ill-defined, or whose result would be 'nonsensical' to humans. 1:与其他任何一个相同,它会阻止你进行不明确的操作,或者对人类造成“无意义”的操作。 Like float addition on integers. 就像浮点数加上整数一样。
2: Nope, the oldest programming language in the world, the (untyped) lambda calculus, is both functional and untyped. 2:Nope是世界上最古老的编程语言,(无类型的)lambda演算,既有功能也有无类型。
3: Hardly, functional just means no side effects, no mutations, referential transparency et cetera. 3:很难,功能只是意味着没有副作用,没有突变,参考透明等等。

Just remember that the oldest functional language, the untyped lambda calculus has no type system. 只记得最古老的函数式语言,无类型的lambda演算没有类型系统。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM