Scala类型系统与Haskell相比的缺点?

Eli*_*der 53 haskell type-systems scala language-comparisons static-typing

我已经读过Scala的类型系统被Java互操作性削弱了,因此无法执行与Haskell类型系统相同的功能.这是真的?因为类型擦除是弱点,还是我在各方面都错了?这是不同的Scala没有类型类的原因吗?

Kev*_*ght 53

最大的区别是Scala没有Hindley-Milner全局类型推断,而是使用一种局部类型推断,要求您指定方法参数的类型和重载或递归函数的返回类型.

这不是由类型擦除或JVM的其他要求驱动的.这里可能遇到的所有困难都可以解决,并且只考虑Jaskell - http://docs.codehaus.org/display/JASKELL/Home

HM推理在面向对象的上下文中不起作用.特别是,当使用类型多态时(与类型类的ad-hoc多态性相反).这对于与其他Java库的强大互操作至关重要,并且(在较小程度上)从JVM获得最佳可能的优化.

说Haskell或Scala有一个更强大的类型系统,只是它们是不同的,这并不是真的有效.两种语言都在不同方向上推动基于类型的编程的界限,并且每种语言都具有难以在另一种语言中复制的独特优势.

  • @Mauricio:是的,OCaml是一个更好的反例,因为它推断了类型...... (10认同)
  • 对于那些遇到这个讨论的人来说,F#**确实需要在某些时候使用类型注释:http://stackoverflow.com/a/2977953/2073130,而OCaml**不是**做同样的事情:http:/ /stackoverflow.com/a/22533286/2073130 (5认同)
  • "HM推理在面向对象的环境中不起作用".但是F#确实实现了HM并且具有面向对象的一面. (4认同)

soc*_*soc 23

Scala的类型系统与Haskell不同,尽管Scala的概念有时直接受到Haskell的优势以及知识渊博的研究人员和专业人士社区的启发.

当然,首先在主要用于函数式编程的VM上运行会产生与针对该平台的现有语言的一些兼容性问题.因为关于类型的大多数推理都是在编译时发生的,所以Java(作为一种语言和一个平台)在运行时的局限性无需担心(除了类型擦除之外,尽管这个错误似乎使得集成到Java中)生态系统更无缝).

据我所知,Java类型系统级别的唯一"妥协"是处理原始类型的特殊语法.虽然Scala甚至不再允许Raw类型,但它接受带有该bug的旧Java类文件.也许你已经看过像List[_](或更长的等价物List[T] forSome { type T })的代码.这是Java的兼容性功能,但在内部也被视为存在类型,并且不会削弱类型系统.

Scala的类型系统确实支持类型类,尽管它比Haskell更冗长.我建议阅读本文,这可能会对Scala的类型系统的相对强度产生不同的印象(第17页的表格是非常强大的类型系统概念的一个很好的列表).

不一定与类型系统的强大功能相关的是Scala和Haskell的编译器用于推断类型的方法,尽管它对人们编写代码的方式有一些影响.拥有强大的类型推理算法可以使编写更抽象的代码变得有价值(你可以自己决定在所有情况下这是否是一件好事).

最后,Scala和Haskell的类型系统是由为用户提供解决问题的最佳工具的愿望驱动的,但是已经采取了不同的途径来实现这一目标.

  • 存在类型与原始类型不完全相同.例如,List [_]不被认为是与另一个List [_]相同的类型 (3认同)

Ich*_*hyo 13

另一个值得考虑的有趣点是Scala直接支持经典的OO风格.这意味着,存在子类型关系(例如,List是Seq的子类).这使得类型推断更加棘手.除此之外,您可以在Scala中混合特征,这意味着给定类型可以具有多个超类型关系(使其更加棘手)


Aar*_*rup 10

Scala没有rank-n类型,尽管在某些情况下可能会解决此限制.


Bri*_*Hsu 8

我对Haskell只有很少的考虑,但最明显的是我注意到与Haskell不同的Scala类型系统是类型推断.

在Scala中,没有全局类型推断,您必须明确告诉函数参数的类型.

例如,在Scala中你需要写这个:

def add (x: Int, y: Int) = x + y
Run Code Online (Sandbox Code Playgroud)

代替

add x y = x + y
Run Code Online (Sandbox Code Playgroud)

当您需要使用泛型版本的add函数时,这可能会导致问题,这些函数适用于各种类型的"+"方法.有一个解决方法,但它会变得更加冗长.

但在实际使用中,我发现Scala的类型系统足够强大,适合日常使用,我几乎从不使用这些解决方法进行通用,也许这是因为我来自Java世界.

而显式声明参数类型的限制并不是一件坏事,无论如何都需要记录它.


小智 6

他们图灵可以减少吗?

请参阅Oleg Kiselyov的页面http://okmij.org/ftp/ ...可以在Haskell的类型系统中实现lambda演算.如果Scala可以做到这一点,那么在某种意义上,Haskell的类型系统和Scala的类型系统会计算相同的类型.问题是:一个人比另一个人更自然吗?一个人比另一个人更优雅?