【问题标题】:Are types and OO coupled?类型和 OO 是耦合的吗?
【发布时间】:2011-04-24 17:07:03
【问题描述】:

试图了解类型是否意味着 OO,反之亦然。

问题:

  • 究竟什么是类型?

  • ruby 中的类可以称为“类型”吗?

  • 在 javascript 中,原生函数/对象,如 Array、String、Function ... 它们是类型吗?

  • C 结构是类型吗?

  • 即使一种语言不支持 OO,它是如何被键入的?例如哈斯克尔。这种语言中的类型是否是“数据”类型,在 OOPL 的对象/类中没有行为(方法)?有类型但没有 OO 的语言和支持 OO 的语言之间在类型上的显着差异是什么?

  • 如果类/对象是类型,OO 不是暗示类型吗?

  • 你能有一个没有 OO 语言中典型层次结构的类型系统吗?

  • 既然 clojure 支持类型提示,那么它在某种意义上可以称为类型化吗?它不是静态类型的。

  • “无类型”和“动态类型”是同一个意思吗?

【问题讨论】:

    标签: javascript ruby oop programming-languages clojure


    【解决方案1】:

    静态类型是程序部分(通常是表达式)的属性,类型检查器将在不执行程序的情况下尝试证明或反驳,可能同时推断该属性。 (实际上,这有点离题,依赖类型和分阶段编译使事实比这更模糊)。从广义上看,动态类型语言具有一种静态类型 - 语法上有效的表达式类型。

    动态类型是“对象”(不一定是 OO 对象)的属性,运行时将在程序执行期间自动检查该属性。每个主流的静态类型语言都有一些动态类型......例如除法函数静态定义为采用两个数字并返回一个数字,但动态定义为第二个数字不能为零。有些静态类型语言的“非零数”可以是静态证明的类型。在许多静态类型语言(例如 Java)中,非 null 是一种动态类型,而在 Haskell 中它是一种静态类型。等等。

    这两者有些相关(它们都是防止未定义行为的方法),但又完全不同,以至于“类型”一词被用来表示两者都是混淆的根源。

    静态和动态类型系统都早于 OO,并且都有出色的非 OO 语言来表示它们(例如 Scheme 和 SML)。事实上,它们早于我们所知的计算机编程。查看可追溯到 1930 年代和 40 年代的无类型和简单类型的 lambda calculii。

    有关差异的更深入讨论,请参阅:http://web.archive.org/web/20080822101209/http://www.pphsg.org/cdsmith/types.html

    有关查看静态和动态类型的某些属性的一种方法,请参阅:http://james-iry.blogspot.com/2010/05/types-la-chart.html

    动态类型和非类型的意思是一样的吗?嗯...无类型来自无类型的 lambda 演算。与其他 lambda 演算(如具有静态类型的简单类型 lambda 演算)相比,它被称为无类型。因此,从这个意义上说,动态类型的语言当然是无类型的。但是……

    与“真正的”编程语言不同,无类型的 lambda 演算具有以下属性:任何语法上有效的表达式都可以“取得进展”,而无需测试任何可能导致未定义行为的属性。不存在除以零、取消引用 null 或向无法处理它的对象发送消息的等价物。因此,可以提出这样的论点:无类型的 LC 没有动态类型系统,即使它是无类型的。

    【讨论】:

      【解决方案2】:

      这是我的看法。类型只是与某些数据结构相关的标签。在 OO 语言中,这些数据结构会以方法的形式携带行为。这些标签有助于了解可以对某些数据结构应用哪些操作(通过对对象的方法调用,或通过将这些数据结构作为参数传递给某些函数)。

      编程语言具有类型系统的一个明确证明是,您有谓词来询问某个值具有什么样的“标签”。在 OO 语言中,这通常是 instanceof 运算符,但它可能采用其他形式(is 运算符、typeof 运算符、is_a() 函数或专用函数:is_stringis_array)。在 Haskell 中,这是通过模式匹配实现的。

      老实说,我还没有见过无类型语言,即完全没有类型的语言。到目前为止,我所看到的语言是:

      - non-inferred statically strongly typed: Java
      - inferred statically strongly typed: Haskell
      - dynamic strongly (explicit coercion between types) typed: Python
      - dynamic loosely (implicit coercion between types) typed: PHP, JavaScript 
      

      【讨论】:

      • +1 不使用动态类型和松散类型作为同义词
      • 在 Haskell 中,你不能对值的类型进行模式匹配,只能对它的结构进行模式匹配。值的类型始终是静态已知的,不能在运行时查询。顺便说一句,我不同意类型必须在运行时可查询才能键入语言的暗示。 C 肯定有类型,但不等同于 typeof 运算符。
      • 这种可查询标签的概念是关于动态类型的。静态类型可能会删除所有这些标签。在基本的 Haskell '98(和 SML)中,无法动态测试类型标签 - 您只能动态测试“构造函数”标签。例如,在 Haskell 中,“newtype”创建了一个与另一种类型具有完全相同表示的类型。两者之间的区别完全从编译的程序中删除,因为区别完全是静态强制执行的。有 10 人对这个答案投了赞成票,但它是错误的,或者至少是不完整的。
      • @delnan:Haskell 中的“类型”这个词有一个非常精确的含义。例如,Maybe () 是具有四个值的单一类型:Maybe ()NothingMaybe _|__|_(其中 _|_ 未定义,现在可以忽略)。仅仅因为您可以对 Maybe ()Nothing 进行模式匹配以区分它们并不会使它们成为不同的类型,就像 0 :: Integer1 :: Integer 是不同的类型一样。它们有不同的“形状”,但都是Maybe ()s 或Integers。
      • @sepp2k,@James Iry,感谢您的反馈。确实,您不能在 Haskell 中的类型上进行模式匹配,但在它的构造函数上。不过,IMO 类型构造函数与类型非常紧密,以至于它是一种查询形式。我的意思是你可以和他们一起做分支。我几乎没有使用 C 的经验,所以我错过了 C 无法查询类型的事实。我想你是对的,类型化的语言不一定有可查询的标签。正如我所说,这就是我看到情况的方式,现在我看到它好一点:)
      【解决方案3】:

      我今天偶然发现了这个,也许它对你有一些很好的意见:

      What to know before debating type systems

      【讨论】:

        【解决方案4】:

        Type System 上的维基百科页面对类型是什么有很好的引用:

        一个易于处理的句法框架,用于根据它们计算的值的种类对短语进行分类

        因此,C 结构是一种类型,您不需要类型的对象。

        基本上,类型是一种决定语言中的值如何以理智的方式组合在一起的方法。您可以通过几种语言看到其中的一些内容:

        在 C 中:

        int x = 'a' + 13; // 110
        char x = 'a' + 13); // 'n'
        

        在 Python 中

        >>> 'a' + 13
        TypeError: cannot concatenate 'str' and 'int' objects
        

        在不同的情况下,这两者都是合理的。这带来了强类型与弱类型的区别。在像 Python 这样的强类型语言中,您不能将一种类型转换为另一种类型。 C 是弱类型,如果你有一个 char 并且想将它转换为一个 FILE,它会让你,以下甚至不会在默认 gcc 中发出警告:

        FILE m = (*(FILE*) 'a')
        

        这并不意味着 C 没有类型,只是在某些情况下可以从一种类型变为不相关的类型。跨语言有一个连续统一体。

        Haskell 是强类型的,如果一个函数接受某些类型的参数并且你试图用不同的类型调用它,它就不会编译。 (根据您的问题,Haskell 不是 OO,但肯定有类型。)

        factorial 0 = 1
        factorial n = n * factorial (n - 1)
        

        如果您尝试使用字符串调用阶乘:阶乘 ("HI") 它将不起作用。请注意,您不必说 n 是一个数字。编译器想通了。这叫做type inferrence。强类型并不意味着您需要明确声明类型。一些语言可以确保在没有 C 和 Java 注释的情况下不会发生类型错误。

        请注意 Haskell 如何在编译时抛出错误。这是另一个有用的区别:静态与动态类型。静态类型在编译时捕获错误。动态类型在运行时捕获它们。上面的 python 在运行时捕获了类型错误,所以 Python 是动态类型的(它也是强类型的)。 Pascal 和 Haskell 一样,是强类型和静态类型的

        【讨论】:

          【解决方案5】:

          究竟什么是类型?

          类型是对潜在值空间和/或其解释的约束。特别是,应用于变量的类型意味着该变量只能保存只能以某些特定方式解释的特定值。 (细节各不相同;对于如何详细阐述该一般原则,存在一些非常不同的意见。)

          ruby 中的类可以称为“类型”吗?

          是的。

          在 javascript 中,原生函数/对象,如 Array、String、Function ...它们是类型吗?

          是的。

          C 结构是类型吗?

          是的。

          一种语言即使不支持 OO 也能被键入是怎么回事?例如哈斯克尔。这种语言中的类型是否是“数据”类型,在 OOPL 的对象/类中没有行为(方法)?有类型但没有 OO 的语言和支持 OO 的语言之间在类型上的显着差异是什么?

          类型的定义与OO无关。

          如果类/对象是类型,OO 不是暗示类型吗?

          形式上,OO的定义与类型无关;对象是状态信息和对其进行操作的封装。然而,这两个概念通常一起使用。

          你能有一个没有 OO 语言中典型层次结构的类型系统吗?

          是的。 C 语言有类型系统,但根本没有对象系统。

          既然 clojure 支持类型提示,那么它在某种意义上可以称为 typed 吗?它不是静态类型的。

          是的。

          'untyped' 和 'dynamically typed' 这两个词意思一样吗?

          没有。无类型(或等同于“如果你只有一把锤子”原则)意味着所有操作都适用于所有值。动态类型意味着值知道自己的类型,因此知道可以对其应用哪些操作,并且在运行时检查类型约束。 (相比之下,在静态类型语言中,通常是 变量 保存类型信息,并且类型约束由编译器检查。)

          【讨论】:

          • 您的答案看起来很像您只是复制了我的答案并使用了正确的引用而不是列表。 ;-)
          • @nebukadnezzar:您并没有真正提供太多见解,但对于其中许多问题,直接“是”是唯一理智的答案。另一方面,我至少费心提供一些解释性的答案。
          • 你确实做到了,我并不是要暗示你的帖子不好。我只是指出显而易见的:-)
          【解决方案6】:

          数据“类型”只是告诉您如何解释字节序列(作为整数、浮点数、数据结构等)。类型使处理原始数据变得更加容易。我无法想象有一种语言在某种程度上没有类型。术语“无类型”通常意味着“隐式类型”。您不必指定数据类型,但编译器/解释器会为您跟踪它。像 TCL 这样的语言似乎没有类型,因为所有数据都被认为是相同的类型(在 TCL 中一切都是字符串)。这并不意味着没有类型,只是程序员不必显式指定它们。

          OO 是一个高级编程概念,与数据类型的概念没有真正的联系。传统上,OO 与诸如类之类的事物相关联。这些是开发人员指定自定义数据类型和定义对该数据类型进行操作的函数的简单方法。许多 OO 概念是建立在数据类型的使用和操作之上的,因此您可以说它们是相关的。但是,“耦合”并不是一个准确的描述。毕竟,许多低级语言(例如 C)有类型但没有 OO。

          【讨论】:

            【解决方案7】:

            晚会,但请阅读 William Cook 的这篇论文:

            http://www.cs.utexas.edu/~wcook/Drafts/2009/essay.pdf

            在我阅读本文之前,OO 和类型之间的关系对我来说也是一个谜。

            【讨论】:

              猜你喜欢
              • 1970-01-01
              • 2015-11-14
              • 1970-01-01
              • 1970-01-01
              • 2013-12-25
              • 2017-05-09
              • 1970-01-01
              • 2017-10-12
              • 1970-01-01
              相关资源
              最近更新 更多