一般来说,Extension用来给Class增加私有属性和方法,写在 Class 的.m文件。但是Extension不是必须要写在.m文件,你可以写在任何地方,只要在 @implementation 前定义就可以。所以我们可以利用这个特性实现属性隐藏。

Case: 模块内部需要访问某属性,模块外需隐藏。这种情况经常会遇到。例如对于某一公司来讲,每个员工都需要员工ID来唯一标识,但是员工作为自然人,在其他地方,别人不需要知道这个ID。所以对于该员工的ID,在公司内部需要访问,在外部需要隐藏。

定义一个company对象,一个person对象。

@interface Person : NSObject

@property (nonatomic, strong) NSString *name;

@end
@interface Company : NSObject

@property (nonatomic, strong) NSString *name;

- (void)addStaff:(Person *)person;

- (void)printAllStaffDisplayName;

@end

公司可以增加一个自然人当自己的员工。可以打印全部员工ID,

@interface Company ()

@property (nonatomic, strong) NSMutableArray<Person *> *staffs;

@end

@implementation Company

- (void)addStaff:(Person *)person {
person.companyID = [NSString stringWithFormat:@"大汉%ld",self.staffs.count];
[self.staffs addObject:person];
} - (void)printAllStaffDisplayName {
for (Person *staff in self.staffs) {
NSLog(@"name:%@ displayName:%@ \n",staff.name,staff.companyID);
}
} - (NSMutableArray<Person *> *)staffs {
if (!_staffs) {
_staffs = [NSMutableArray arrayWithCapacity:];
}
return _staffs;
} @end

可以看到在 Company 中需要访问 Person 的 companyID,所以我们给 Person 增加一个 Extention。写在 Company.h。

@interface Company : NSObject

@property (nonatomic, strong) NSString *name;

- (void)addStaff:(Person *)person;

- (void)printAllStaffCompanyID;

@end

@interface Person ()

@property (nonatomic, strong) NSString *companyID;

@end

这样我们就可以在模块内部增加了一个public属性,而模块外部不知道有这个属性。

    Company *cisco = [Company new];
cisco.name = @"cisco"; Person *tao = [Person new];
tao.name = @"涛"; [cisco addStaff:tao];
[cisco printAllStaffDisplayName];

关于这个特性,可以参考sunny的文章:http://blog.sunnyxx.com/2016/04/22/objc-class-extension-tips/。但是,当你运行的时候会发现,crash了!log显示找不到setCompanyID方法,原来我们把extention写在非.m文件的时候,oc不会帮我们自动生成set,get方法。我想手动写一个set方法来解决这个问题,发现如果想在 @implenmatation 写,就必须知道他的实例变量 _companyID,我们现在拿不到。联想到readOnly属性可以使用 extention 在.m中修改为readWrite:

.h

@interface Person : NSObject

@property (readonly, nonatomic, strong) NSString *gender;

@end

.m

@interface Person ()

@property (nonatomic, strong) NSString *gender;

@end

@implementation Person

@end

那我们也可以在 Person.m 中再次申明一个companyID的私有属性。这样,oc会帮我们自动生成set,get方法。试验一下,完美!

@interface Person ()

@property (nonatomic, strong) NSString *companyID;

@end

@implementation Person

@end

Demo下载

巧用 Class Extension 隐藏属性的更多相关文章

  1. Dos命令的巧用 - 转载

    Dos命令的巧用 豪华绚丽的Windows让人们把DOS抛到遥远的记忆角落,然而,真正有价值的东西不会轻易退出历史的舞台.很多人都已经习惯于 Windows的图形化用户界面,熟不知古老的DOS命令却可 ...

  2. 完美实现保存和加载easyui datagrid自定义调整列宽位置隐藏属性功能

    需求&场景 例表查询是业务系统中使用最多也是最基础功能,但也是调整最平凡,不同的用户对数据的要求也不一样,所以在系统正式使用后,做为开发恨不得坐在业务边上,根据他们的要求进行调整,需要调整最多 ...

  3. 152-技巧-Power Query 快速合并文件夹中表格之自定义函数 TableXlsxCsv

    152-技巧-Power Query 快速合并文件夹中表格之自定义函数 TableXlsxCsv 附件下载地址:https://jiaopengzi.com/2602.html 一.背景 在我们使用 ...

  4. Windbg Extension NetExt 使用指南 【2】 ---- NetExt 的基本命令介绍

    摘要 : 本章节介绍NetExt常用的命令. 并且对SOS进行一些对比. NetExt的帮助 要想玩好NetExt, 入门就得看帮助. 看NetExt的帮助可以调用!whelp 命令. 这样hi列举出 ...

  5. Windbg Extension NetExt 使用指南 【1】 ---- NetExt 介绍

    摘要 : 在使用WINDBG做debugging的时候,需要一个好的工具帮助进行数据分析. 最常见的extension包括SOS, PSSCOR.  NetExt则是另外一种提供了丰富命令功能的deb ...

  6. 「译」JUnit 5 系列:扩展模型(Extension Model)

    原文地址:http://blog.codefx.org/design/architecture/junit-5-extension-model/ 原文日期:11, Apr, 2016 译文首发:Lin ...

  7. PHPmailer关于Extension missing: openssl报错的解决

    最近在写一个网页的时候,需要用到PHPmailer来发送邮件,按照官网上给出的demo写出一个例子,却报错Extension missing: openssl 最后发现需要修改php.ini中的配置: ...

  8. [MySQL性能优化系列]巧用索引

    1. 普通青年的索引使用方式 假设我们有一个用户表 tb_user,内容如下: name age sex jack 22 男 rose 21 女 tom 20 男 ... ... ... 执行SQL语 ...

  9. 研究Extension和Category的一个例子

    Category: 1. 无法添加实例变量 2.将类的实现分散到多个不同文件或多个不同框架中. Extension: 1. 可以添加实例变量 注: 如果Category的头文件中也使用Extensio ...

随机推荐

  1. BZOJ 2127 / Luogu P1646 [国家集训队]happiness (最小割)

    题面 BZOJ传送门 Luogu传送门 分析 这道题又出现了二元关系,于是我们只需要解方程确定怎么连边就行了 假设跟SSS分在一块是选文科,跟TTT分在一块是选理科,先加上所有的收益,再来考虑如何让需 ...

  2. Entity Framework学习过程

    ///安装ef nuget中文控制台指令 PM> Install-Package EntityFramework.zh-Hans <!--配置数据库连接--> <connect ...

  3. 2019巅峰极客CTF-web1(LOL英雄联盟)

    今晚有空 以后随缘写博客了 好好沉淀 web1当天做出的队伍很少 其实不难    折腾到最后就差一步  可惜    0x01 读取文件 截图没留了 只留了代码部分. 有个页面  有上传和下载功能 起初 ...

  4. 求ascii 然后做运算

    介绍 ABC 返回每个字符的ascii A->65 B->66 C->77 组成656667 把所有的7替换成1 然后变成 656667 和 656661 每个数值做加法 然后做减法 ...

  5. cas系列-cas server demo搭建(二)

    一 部署简述 cas server官方推荐采用overlay方式进行部署,通过替换自定义文件,减少项目文件改动,以简化开发和部署,这个有点类似于项目上直接替换java的class文件,由于和git的搭 ...

  6. git reset 版本回退操作

    1 git回退命令 git reset --hard GIT_HEAD   GIT_HEAD是你具体要回退的分支: 如图:   注:  查询GIT_HEAD可以通过两个命令:git log 获取未删除 ...

  7. 5.3.3 自定义writable和RawComparatorWritable

    5.3.3 自定义writable (1)构造员工writable Hadoop虽然已经实现了一些非常有用的Writable,而且你可以使用他们的组合做很多事情,但是如果你想构造一些更加复杂的结果,你 ...

  8. Ubuntu下制作deb包的方法详解

    1  认识deb包 1.1   认识deb包 deb是Unix系统(其实主要是Linux)下的安装包,基于 tar 包,因此本身会记录文件的权限(读/写/可执行)以及所有者/用户组. 由于 Unix ...

  9. Vue开发工具VS Code与调试

    vscode安装 进入vscode官网(https://code.visualstudio.com/Download)vscode插件安装进入vscode官网插件商店(https://marketpl ...

  10. Kontln的属性形式Getter和Setter

    package loaderman.demo class Person { val name: String get() = "name" var v: Int = 0 var v ...