【问题标题】:Is type also object in Swift? and what's the meaning of sending a message to an objectSwift 中的类型也是对象吗?以及向对象发送消息是什么意思
【发布时间】:2017-01-17 14:53:56
【问题描述】:

这可能不是语言相关问题的特殊性。由于 Swift 是我目前正在学习的语言,所以我在这里使用它。

我从 Matt Neuburg 的书 iOS 10 Programming basics with Swift 中摘录了这句话

In Swift, "everything is an object" and an object

Object is something you can send a message to.

让我们添加一个示例。假设有一个名为 Dog 的客户类型。它具有 bark() 和 sit() 功能。两个名为 fido 和 rover 的 Dog 类型实例已启动。

In swift, the syntax of message-sending is dot-notating, like

fido.bark()
rover.sit()
rover.printName()

The above code lines means sending message to object fido and rover

问题 1:

为什么描述是:向对象 fido 和 rover 发送消息?在我看来,对象 fido 和 rover 发送了一些消息以在控制台中将其打印出来(例如 printName() ),而不是我们向它发送消息。 .bark() 看起来它会让 fido 做某事并向外部世界发出反应,因为 bark() 是它腹部的功能,而不是我们的东西创建并注入它的身体。我们只是通知这个函数它的工作时间。难道这个informing object做某件事就是向对象发送消息的意思吗?

问题 2:

"In Swift, everything is an object", an object is something you can send message to 

如果我理解正确的话,即使对象类型本身也是一个对象。例如 String、Int 或 Double。因为 type 具有 type 属性,这意味着您可以向它发送消息

非常感谢您的宝贵时间

【问题讨论】:

  • “消息”语言学源于将 Swift 与其密切相关的老兄弟 Objective-C 进行比较,后者并不容易直接转化为我们人类所说的“消息”。我引用programming with Objective-C:“发送一个Objective-C消息在概念上非常像调用一个C函数”
  • @dfri 所以这里“发送”消息大致相当于“调用”C 内容中的函数
  • 第一个问题,你可以简单理解:向对象发送消息调用对象的函数。这是 Apple 在其关于 Objective-C 的文档中使用的表达式。
  • @Hoa,实际上他们从Smalltalk 借用了sending message 表达式,这是最早的OOP 语言之一。 ObjC 括号语法也基于Smalltalk 语法。
  • 至于问题2,见the following Q&A,描述得很好:“消息发送是这样执行的:[obj message]。本质上,Obj-C中的对象就是任何响应的东西到消息。这意味着即使类也是对象。”.

标签: swift object message


【解决方案1】:

OOP 世界中存在一些关于“消息传递”与“方法调用”的争论,无论是在我们如何谈论它们以及如何实现它们方面。在原型 OOP 语言(SmallTalk,ObjC 的后代)中,一切都是“消息”。我捆绑了一条消息(这是一个真正的数据结构,NSInvocation 是 Cocoa 中最重量级的形式),并将其传递到对象的收件箱,然后它处理消息并执行一些操作。

大多数常见的 OOP 语言都没有采用这种模型(当某些东西今天采用时,我们倾向于称它为“演员”而不是“对象”)。 C++ 极大地启发了当前大多数“面向对象”语言,它采用了“方法调用”方法。这与函数调用更加一致,并且与跳转到内存中的特定点并在那里执行指令有关。方法调用比消息传递更静态。在运行时完全重新配置消息的处理方式、创建新的消息处理程序、重新路由旧的消息处理程序等要容易得多。方法调用要快得多。

在实践中,大多数呼叫站点的大多数程序都没有太大差异。绝大多数 ObjC“消息”都精确地 1:1 转换为方法调用,并且系统几乎总是避免生成完整的 NSInvocation 消息(它们非常昂贵)。

但是当我们教授 OOP 时,我们仍然在概念上混合了这两种想法,这就是这里发生的事情。 (Swift 也恰好大量使用了这两种机制。)

考虑fido.bark() 的一个好方法是“向fido 发送不带参数的bark 消息”。然后由 Fido 决定如何处理。在实践中,消息通常被理解为“命令”,因为对象不“决定”做什么。但原则上可能会。例如,Fido 可能是一只非常聪明的狗,并且决定不叫,因为它已经深夜了,即使你告诉他这样做,或者他可能睡着了,他那时不喜欢吠叫。对象的概念是它们封装了知识和状态。

对于第二个问题,Swift 中的类型不是完整的对象。它们是“元对象”。您可以向它们发送消息是绝对正确的,因此它们在某些方面表现得像对象。但是 Swift 没有“第一类类型”,这意味着不是所有你可以用一个对象做的事情都可以用一个类型来做。但是,是的,您绝对是在正确的道路上,在许多情况下您可以将类型视为对象。

(一个主要的 Swift 特性要求是通过添加一个称为 Higher Kinded 类型的概念来使类型更加一流。这将使得可以在 Array 本身上编写方法,而不仅仅是在 Array<T> 上编写方法,并且有些类型,比如 Functor,完全可以写。)

【讨论】:

  • 非常感谢您提供如此清晰详细的解释!
【解决方案2】:

我也在读一本书《iOS 9 Programming Fundamentals with Swift》,其中有一些有趣的方面来看待“一切都是 swift 中的对象”。

“在 Swift 中,一切都是对象”,对象是你可以向其发送消息的东西

在swift中,我们可以为String、Int、Double...等添加扩展

例如。

extension Int {
func sayHello() {
    print("Hello, I'm \(self)")
    }
}
1.sayHello() // outputs: "Hello, I'm 1"

这里的1不是类或实例,它是一个结构体。 Swift 有三种对象类型:类、结构和枚举。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2011-06-12
    相关资源
    最近更新 更多