求批评:我对objective c的几个特性的理解对么?

2012-02-14 22:10:05 +08:00
 myrual
objective c提供了几个有趣的特性,category, protocol, message forward.
都可以在不写新class的情况下给既有class添加功能,
category 适用于给一个既有class添加新消息接口,
protocol适用于给若干个class添加相同接口,
message forward适合把一个class作为入口,调用其他class。
都可以做到少写新的class,不知道这么的设计初衷是什么
3772 次点击
所在节点    iDev
5 条回复
lldong
2012-02-14 23:21:52 +08:00
Objective-C的设计受到Smalltalk很大的影响,为了方便代码维护,所以从Smalltalk借鉴了category的概念,让你能够将一个类的实现分割到不同文件中。

protocol只是定义接口,并不能添加实现(功能),类似于Java中的interface(据说Java中的interface就是从Objective-C中借鉴过来的)。

message forward是Objective-C消息机制的一部分,让对象在接收到一个无法识别的消息后能在运行时处理这个错误,像NSProxy也是利用了这个机制。
myrual
2012-02-14 23:54:17 +08:00
@lldong 对象什么情况下会接受到一个无法识别的消息呢?
或者说什么情况下会给一个对象发一个无法处理的消息呢?
从我的理解来说大概的场景是:
class b 实现了一个消息处理过程
class a 原本不需要这个消息处理过程,但是后来又希望class a能处理该消息,所以用forward可以不用重复写代码,也不用修改继承关系。
lldong
2012-02-15 00:14:20 +08:00
@myrual 简单来说,比如你有一个你有一个Foo对象foo,但它没有实现bar方法。现在你调用你发送[foo bar], 这是它会根据foo的isa指针(该指针指向其类对象,在Objective-C里面类也是一个对象)查找该方法的实现,如果没有,它会去其父类查找如此下去,如果最后还是找不到就会进入一个fallback:
1. 调用 resolveInstanceMethod,你可以在这里动态添加一个实现,并返回YES.
2. 如果第一步返回NO,回进入 forwardingTargetForSelector:, 可以给这个消息指定一个新的target,如果没有则进入第三步
3. forwardInvocation,你可以构建一个NSInvocation
如果这三步都没结果就会抛异常了。
myrual
2012-02-15 00:21:41 +08:00
@lldong 真详细。比我看的电子书还多介绍了两个。书里只讲了第三个方法。
动态添加的意思是说在调用[foo bar]的源代码文件里面直接写一个实现么?
还是在实现Foo的源代码文件里面写一个实现?
谢谢
lldong
2012-02-15 00:49:41 +08:00
@myrual 你书上的forwarding指的是第三步吧,添加的话要用到运行时API, class_addMethod(), 是C的接口. 具体在Runtime Programming Guide里有介绍。

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/27362

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX