在Apple发布Xcode7的时候,不仅把Swift编程语言升级到了2.0版本,而且还对Objective-C做了许多提升,包括引入__nonnull/__nullable。其中,对于Objective-C编程语言本身而言,更为有用的便是轻量级泛型。

其中,比较明显的体现就是NSArray、NSDictionary这些容器类都采用了新引入的轻量级泛型。通过轻量级泛型,我们可以非常容易地获取其中的元素,并访问其相印特有的属性和方法。我们举一个简单例子来阐明轻量级线程带来的方便:

    // 不带泛型的情况
NSArray *numArray = @[@, @, @];
int sum = [(NSNumber*)numArray[] intValue] + [(NSNumber*)numArray[] intValue] + [(NSNumber*)numArray[] intValue]; // 使用泛型的情况
NSArray<NSNumber*> *numArray = @[@, @, @];
int sum = [numArray[] intValue] + [numArray[] intValue] + [numArray[] intValue];

我们通过上述例子就能看到轻量级泛型带来的语法上的便利性,即它是一块甜美的语法糖(syntax sugar)。

之前Apple LLVM 6.0对C11标准的泛型——generic selection在Objective-C上支持得还不够良好,但Apple LLVM 7.0上已经能完美支持了。比如下述例子:

    int flag = _Generic(@, NSNumber*:, NSString*:, int:, default:);
NSLog(@"The flag is: %d", flag);

上述代码将成功地输出“The flag is: 1”。

与C11的generic selection所不同的是,Objective-C自带的泛型其本质为covariant type,即协变类型。也就是,其泛型与Java的有些类似。它要求泛型必须是一个Objective-C类类型,即至少为id类型。对于上述NSArray的例子,我们在声明一个Objective-C对象引用时,通过在类名后面添加<NSNumber*>来指明当前NSArray里的元素都是NSNumber*类或其子类类型。这样,我们在访问其元素时可直接访问其intValue方法。

下面我们介绍如何自己定义一个泛型类。其语法描述如下:

@interface    class_name    <    __covariant    type_identifier    >    inherit_expression

这里,class_name就是类名;type_identifier是类型标识符,该标识符可以由程序员自己命名;最后的inherit_expression表示继承某个父类以及/或实现某些协议。

这里引入了一个新的关键字——__covariant,表示后面的type_identifier是一个泛型类型。该泛型类型在声明一个对象时进行具体指明。

下面举一个具体的例子来说明如何具体使用Objective-C泛型。

@interface MyObject<__covariant T> : NSObject
{
@private T obj;
}

@property (nonatomic, retain) T obj;

@end

@implementation MyObject

@synthesize obj;

- (void)dealloc
{
if(obj != nil)
[obj release]; NSLog(@"My object deallocated!");
[super dealloc];
} @end @implementation ViewController - (void)viewDidLoad { MyObject<NSNumber*> *numObj = [[MyObject alloc] init];
numObj.obj = @;
[numObj release]; MyObject<NSString*> *strObj = [[MyObject alloc] init];
strObj.obj = @"Hello, world";
[strObj release];
} @end

上述代码,我们定义了一个MyObject的泛型类,其泛型标识符用T表示。随后,我们用该泛型T定义了一个私有对象obj,并用它作为一个property。

随后,我们在viewDidLoad方法里用MyObject<NSNumber*>声明了一个对象numObj;用MyObject<NSString*>声明了一个strObj对象。我们后面可以直接通过numObj.obj调用intValue来访问其int值;直接通过strObj.obj来调用length方法以获得其字符串长度。

Objective-C轻量级泛型的更多相关文章

  1. iOS开发——新特性OC篇&Objective新特性

    Objective新特性 Overview 自 WWDC 2015 推出和开源 Swift 2.0 后,大家对 Swift 的热情又一次高涨起来,在羡慕创业公司的朋友们大谈 Swift 新特性的同时, ...

  2. nullable,kindof,泛型新特性

    文章来自: http://blog.csdn.net/majiakun1/article/details/46530245 Overview 自 WWDC 2015 推出和开源 Swift 2.0 后 ...

  3. Objective-C的泛型

    WWDC2015的明星是Swift.在Swift语言到2.0以后会被开源,这其中包括了protocol扩展和一个新的错误处理API. 苹果的小baby已经长成,并且意料之中的获得了开发者的关注.但是在 ...

  4. Swift & OC 混编 浅析

    转载自:http://www.infoq.com/cn/articles/wangyi-cartoon-swift-mixed-practice?utm_campaign=rightbar_v2&am ...

  5. 2015&nbsp;Objective-C&nbsp;三大新特性

    Overview 自 WWDC 2015 推出和开源 Swift 2.0 后,大家对 Swift 的热情又一次高涨起来,在羡慕创业公司的朋友们大谈 Swift 新特性的同时,也有很多像我一样工作上依然 ...

  6. 【转载】2015 Objective-C 三大新特性 | 干货

    Overview 自 WWDC 2015 推出和开源 Swift 2.0 后,大家对 Swift 的热情又一次高涨起来,在羡慕创业公司的朋友们大谈 Swift 新特性的同时,也有很多像我一样工作上依然 ...

  7. Objective-C 语言特点/特性

    Objective-C中 1.所有的类都必须继承自NSObject. 2.所有对象都是指针的形式. 3.用self代替this. 4.使用id代替void*. 5.使用nil表示NULL, 6.只支持 ...

  8. ios学习路线—Objective-C(新特性)

    1.方法顺序无关 Objective-C类由声明文件h和实现文件m组成,所有的public方法都在h文件中声明,private方法可以写在m文件中,但是在早期的编译环境中需要注意方法的顺序,例如下面的 ...

  9. YYModel源代码阅读--基础知识

    这段时间因为工作需要,阅读了YYModel这个开源框架,至于它能做什么,最直白的讲述就是JSON与Model之间的相互转化. 源代码在Github,大家可以自行git clone或者download. ...

随机推荐

  1. Follow My Heart

    看到这个题目,能够让我不断跟随自己的心去奋斗,当然在这之中也有过彷徨,有过偷懒,但最终还是依然坚强,依然保持着一种积极向上的心情去迎接每一天. 这一年从大三升到大四,瞬间觉得自己成长了很多,身上的责任 ...

  2. flask框架下读取mysql数据 转换成json格式API

    研究了一天 因为需要从数据库拿数据然后转换成json的格式 expose出去为 API 发现一条数据是容易,两条以上我居然搞了这么久 好歹出来了 先贴一下 后面更新 mysql的操作 比较容易了htt ...

  3. Dynamics 365 目录

    Dynamics 365 目录 1.Dynamics 365 on-premises 安装 2.Dynamics 365 安装过程中的问题 2.1Dynamics 365 安装问题——无法访MSCRM ...

  4. 自定义异步IO框架

    异步就是回调 异步 = 非阻塞+循环 select只能完成IO多路复用,不能完成异步 IO多路复用--->监听多个socket对象,这个过程是同步的 利用其特性可以开发异步模块 异步IO:非阻塞 ...

  5. nachos3.4 threads管理 (c++)

    Main.cc //引导代码初始化操作系统内核.允许直接调用内部操作系统功能,简化调试和测试.在实践中,bootstrap代码只会初始化数据结构, //并启动一个用户程序来打印登录提示.//许多内容只 ...

  6. LightOJ - 1173 - The Vindictive Coachf(DP)

    链接: https://vjudge.net/problem/LightOJ-1173 题意: The coach of a football team, after suffering for ye ...

  7. 判断指定对象是否进入浏览器可视窗口,true 进入,false 没进入

    //判断指定对象是否进入浏览器可视窗口,true 进入,false 没进入 var $win = $(window);//jQuery 的 window 对象 即:文档对象 function isVi ...

  8. P3709 大爷的字符串题 脑子+莫队

    简化题意:区间众数出现次数??? 为什么?原因是,贪心的想,我们要划分成尽量少的严格递增序列,这样rp掉的最少. 设区间众数出现次数为 \(x\) ,那我们至少要分成 \(x\) 段严格上升序列. # ...

  9. Oracle trunc() 日期、数字截取函数

    --Oracle trunc()函数的用法/**************日期********************/1.select trunc(sysdate) from dual --2013- ...

  10. Kubernetes 学习18配置网络插件flannel

    一.概述 1.我们在学习docker时知道docker有四种常用的网络模型 a.bridge:桥接式网络 b.joined:联盟式网络,共享使用另外一个容器的网络名称空间 b.opened:容器直接共 ...