分类,多继承

谈谈你对分类Category的理解

使用场景:可以减少单个文件体积;可以按照功能分组,放到不同的分类里,使结构更清晰;降低耦合性,一个类可以有多个开发人员进行开发;模拟多继承。

Category的实现原理:Category编译之后的底层结构是结构体 category_t ,里面存储着分类的对象方法、类方法、属性、协议等信息。在程序运行的时候,runtime会将category中的数据,合并到类信息中(类对象、元类对象)


Category与 Extension的区别是什么:

1、Category 原则上只能增加方法,能添加属性但是需要配合runtime才能解决没有setter和getter的问题,这一点前文中有说明,下文中等下也再提一下。

2、Extension不仅可以添加方法,还可以增加属性,只是属性默认的访问权限是private。

3、Extension 中生命的方法没有在.m 文件中实现,编译器会报警,但是在Category中的方法没有实现,编译器没有任何警告。这是因为Extension是在编译阶段添加到类中的,而Category是在运行时添加到类中的。

如何通过Category实现多继承?

比如有TestA和TestB两个类,如图


现在想实现一个TestC,让TestC同时继承TestA,和TestB。实现如下




测试结果如下


以上是通过分类的方式。还可以通过消息转发的方式:(先注释掉分类中的所有代码,再加消息转发代码)


这里方法签名、和forwardInvocation的方式我就不展示了,之前的文章中有讲过

测试结果:


可以看到。我们在调用c 执行playBasketBall和playFootBall时,其实调用到的是A 和B的方法。这里抛一个问题出来,假设我在消息转发时这样写:把setAge:  age这些也加到消息转发里,那么,外面在给C设置age的时候,调用的是谁的set方法、get方法?

答案是,调用c自己的set方法,因为进入消息转发前,需要先经过消息发送、动态方法解析。 当c本身就有setAge方法时,在消息发送阶段就可以找到自己的setAge,直接调用自己的setter了,根本走不到消息转发这个环节来。

当然上述两个方法应该也可以配合使用,有兴趣可以自己写demo试试。

还有什么方式可以实现呢?

比如组合拳,C 先继承A,然后C再强引用一个B的对象,这样不管是调A的方法还是B的方法,都可以。

再比如协议,把A、B中需要继承的方法,写到协议里,然后C遵循这两个协议,就可以在C中拥有A、B的方法了。

有兴趣可以写demo试试

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

友情链接更多精彩内容