ObjCMixin:在 Object-C 里实现类似 ruby 的 mixin 机制

项目地址:https://github.com/huandu/ObjCMixin
CocoaPods:pod 'ObjCMixin', '~> 0.1.0'

这是一个脑洞大开的项目……

起因是我看到了 ObjectiveMixin 项目,它可以动态的为 Object-C class 合并其他 class 的功能,但可惜不是很完美,主要存在两个问题:

  • 没有类似 ruby 的 mixin 语法,不够酷炫;
  • Class 的方法修饰其实只是一次性的过程,无需每次 alloc 对象前来做,所以如何能够保证只做一次。

那么 ObjCMixin 实现了什么呢?来来来,我们看看它的威力。

首先,需要声明一个 module 用来做 mixin。

objc// MyModule.h
#import "Mixin.h"

@module(MyModule)
-(void)hello;
@end

实现 module 的函数。

objc// MyModule.m
#import "MyModule.h"

@module_implementation(MyModule)

-(void)hello
{
    NSLog(@"Hello, mixin!");
}

@end

在一个新的 interface 里面使用这个 mixin。

objc// Foo.h
#import "MyModule.h"

// Foo derives from a special base class.
@interface Foo : NSException<MyModule>
@end

在实现文件里面将 MyModule 混合到 Foo 里面。

objc// Foo.m
#import "Foo.h"

@mixin(Foo, MyModule)

@implementation Foo
@end

奇迹般的,Foo 可以使用 MyModule 的所有方法了。

objcFoo *f = [[Foo alloc] init];
[f hello]; // Print "Hello, mixin!" in console.

实现方法极度简单,说出来就会感觉很 low。

主要两点:

  • 用 Object-C runtime api 来复制 class 的方法到另一个 class,详见 class_addMethod 的文档;
  • __attribute__((constructor)) 来声明一个在 main 之前执行的函数,用来一次性的污染 class 方法,干净清晰。

至于有什么用处?好问题,我还没想到!

也许这种 mixin 可以一定程度上满足多继承的需求,例如某些 category 代码不方便通过继承进行耦合,但是代码本身可以重复,那可以考虑一试。

    原文作者:huandu
    原文地址: https://segmentfault.com/a/1190000002877001
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞