链式编程思想

链式编程是什么

链式编程就是将调用多个方法用点语法连接起来,让代码更加简洁和可读性更高
刚开始接触链式编程是Masonry,用起来真的非常爽

1
make.left.right.top.equalTo(self.view);

这样一句语句就调用了4个方法
.left调用了left属性的get方法
.right, .top调用了right和top方法
.equalTo()调用了equalTo方法

这种写法极大简化了写约束的方式

原理

原理就是调用的属性的类型或者方法的返回类型为原调用属性的类型
例如说UILabel调用了某个方法或者属性,得到的类型还是UILabel,那么还可以继续调用UILabel的属性或者方法

如何实现

看了Masonry,我发现有两种实现方式

1.用点语法调用方法

这个其实我之前没发现,写习惯了用方括号调用方法
例如创建一个label 可以这样写UILabel *label = [[UILabel alloc] init
其实也可以这样写UILabel *label = UILabel.alloc.init
不过后种方法几乎没人用,苹果应该也不推荐这种写法,因为有时候这样写是没有代码提示的
但是有一个缺点就是不能调用有参数的方法,所以我们只能写没有参数的方法

创建一个UIButton的分类
写两个方法

1
2
- (UIButton *)setTextHello;
- (UIButton *)setTextColorRed;

并且实现

1
2
3
4
5
6
7
8
9
10
11
- (UIButton *)setTextColorRed
{
[self setTitleColor:[UIColor redColor] forState:UIControlStateNormal];
return self;
} - (UIButton *)setImage
{
[self setImage:[UIImage imageNamed:@"Stan1"] forState:UIControlStateNormal];
return self;
}

然后我们创建一个按钮的时候就可以这样写

1
2
3
4
5
//创建一个按钮
UIButton *button = [UIButton buttonWithType:UIButtonTypeInfoLight];
button.frame = CGRectMake(100, 100, 100, 100);
button.setTextHello.setTextColorRed;
[self.view addSubview:button];

效果如图

但是会报一个警告,因为调用的是属性,但是这个属性没有被用到
解决方法是在调用属性前面加(void),这样就可以了

2.用属性调用

新创建一个UILabel的分类
如果要传入参数的话,就返回一个UILabel的block,可以在block里面实现你想要实现的东西

1
2
3
@property(nonatomic,copy) UILabel* (^kText)(NSString *text);
@property(nonatomic,copy) UILabel* (^kFont)(NSUInteger fontSize);
@property(nonatomic,copy) UILabel* (^kTextColor)(UIColor *color);

加k是为了易于区分,可以不加的
因为这是在分类里面的属性,不会生成setter和getter方法,所以都要自己写
实现如下

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
- (UILabel *(^)(NSUInteger))kFont
{
return ^(NSUInteger font){
[self setFont:[UIFont systemFontOfSize:font]];
return self;
};
} - (UILabel *(^)(NSString *))kText
{
return ^(NSString *text){
[self setText:text];
return self;
};
} - (UILabel *(^)(UIColor *))kTextColor
{
return ^(UIColor *color){
[self setTextColor:color];
return self;
};
} - (void)setKFont:(UILabel *(^)(NSUInteger))kFont{}
- (void)setKText:(UILabel *(^)(NSString *))kText{}
- (void)setKTextColor:(UILabel *(^)(UIColor *))kTextColor{}

不会用到setter方法,也不能用,所以setter方法设为空
然后就能愉快的链式编程了

然后我再想,假如没有参数呢,刚开始是想block没有参数

1
2
3
@property(nonatomic,copy) UILabel* (^aText)();
@property(nonatomic,copy) UILabel* (^aFont)();
@property(nonatomic,copy) UILabel* (^aTextColor)();

实现

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
- (UILabel *(^)())aFont
{
return ^(){
[self setFont:[UIFont systemFontOfSize:16.0f]];
return self;
};
} - (UILabel *(^)())aTextColor
{
return ^(){
[self setTextColor:[UIColor cyanColor]];
return self;
};
} - (UILabel *(^)())aText
{
return ^(){
[self setText:@"这还是一个label"];
return self;
};
} - (void)setAFont:(UILabel *(^)())aFont{}
- (void)setAText:(UILabel *(^)())aText{}
- (void)setATextColor:(UILabel *(^)())aTextColor{}

后来发现调用的时候还是要这样

尝试了一下,最后一个调用能去掉括号,报警告,能运行,但是没效果

所以我想为什么不直接调用属性

1
2
3
@property(nonatomic,strong) UILabel *bText;
@property(nonatomic,strong) UILabel *bFont;
@property(nonatomic,strong) UILabel *bTextColor;

getter && setter

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
- (UILabel *)bText
{
[self setText:@"labellabel"];
return self;
} - (UILabel *)bTextColor
{
[self setTextColor:[UIColor purpleColor]];
return self;
} - (UILabel *)bFont
{
[self setFont:[UIFont systemFontOfSize:13.0f]];
return self;
} - (void)setBFont:(UILabel *)bFont{}
- (void)setBText:(UILabel *)bText{}
- (void)setBTextColor:(UILabel *)bTextColor{}

调用

1
2
3
UILabel *label3 = [[UILabel alloc] initWithFrame:CGRectMake(100, 400, 200, 100)];
(void)label3.bTextColor.bText.bFont;
[self.view addSubview:label3];

如果调用不加(void)还是会报警告
如果想像Masonry那样的链式编程可以这样写

1
2
3
UILabel *label3 = [[UILabel alloc] initWithFrame:CGRectMake(100, 400, 200, 100)];
label3.bTextColor.bText.kFont(30);
[self.view addSubview:label3];

这样就不会报警告,整洁清晰

还发表在 我的个人博客

Objective-C 链式编程思想的更多相关文章

  1. iOS 开发之使用链式编程思想实现简单的计算器

    链式编程思想是将多个操作(多行代码)通过点号(.)链接在一起成为一句代码,使代码可读性好.例如 a(1).b(2).c(3). 链式编程思想最为关键的是,方法的返回值是block,block必须返回对 ...

  2. 模仿Masonry链式编程思想

    使用masonry 也将近一年多了,它的链式编程方式一直是很吸引我的. 之前一直没空好好思考它是如何实现,直到现在正好自己有空,因此写下链式编程的基本思路. 链式基本的编程形式如 a.property ...

  3. ASP.NET MVC学前篇之扩展方法、链式编程

    ASP.NET MVC学前篇之扩展方法.链式编程 前言 目的没有别的,就是介绍几点在ASP.NETMVC 用到C#语言特性,还有一些其他琐碎的知识点,强行的划分一个范围的话,只能说都跟MVC有关,有的 ...

  4. ios的链式编程笔记

    1.Masonry的语法为啥能连续的使用点语法? >> 底层使用的是:用block当函数的返回参数  > 链式编程思想 2. 使用block当函数的返回参数 // 之前开发中比较习惯 ...

  5. 由表单验证说起,关于在C#中尝试链式编程的实践

    在web开发中必不可少的会遇到表单验证的问题,为避免数据在写入到数据库时出现异常,一般比较安全的做法是前端会先做一次验证,通过后把数据提交到后端再验证一次,因为仅仅靠前端验证是不安全的,有太多的htt ...

  6. iOS 链式编程探索(Masonry)

    看了几篇关于链式编程的文章,还是理解的不透彻,我想这可能是因为我自己对block掌握的不熟练. 我已经明白了,所以,和大家分享一下我的理解!如有问题,麻烦大家指出! 直接看代码吧!关键的注释都有. 我 ...

  7. 原生JS实现jquery的链式编程。

    这是我根据之前遇到的一个面试题,题目:用原生JS实现$("#ct").on("click",fn).attr("id"). 然后看了篇jqu ...

  8. Java链式编程接口

    在android开发中显示一个AlertDialog时,常采用下列的写法: new AlertDialog.Builder(getApplicationContext()) .setTitle(&qu ...

  9. JavaScript系列:模块化与链式编程

    模块化:闭包和和函数作用域(JS没有块级作用域ES6之前)构造模块 var man=function(){ var age=12; return { getYear:function(){ retur ...

随机推荐

  1. VS2010/MFC对话框:一般属性页对话框的创建及显示

    一般属性页对话框的创建及显示 本节将介绍一般属性页对话框的创建和显示. 实际上,一般属性页对话框的创建和显示过程和向导对话框是很类似的.鸡啄米将上一节中的向导对话框进行少量修改,使其成为一般属性页对话 ...

  2. Java 根据comboBox选择结果显示JTable

    处理这样的问题的主要思路是:     对于JTable,JTree等Swing控件,都有一个对应的Model用来存储数据,JTable对应的有一个DefaultTableModel.     Defa ...

  3. openstack windows 2008 img

    1,制作镜像主机pre Env yum -y install qemu-img virt-install libvirt 2,配置bridge

  4. Quick Tip: Outline Elements on Hover

    How to get the xpath by clicking an html element How to get the xpath by clicking an html element Qu ...

  5. Uber 司机有话说:你以为当个 Uber 司机很轻松?大错特错!

    Uber 最近的负面新闻越来越多.各方成员都在抨击.斥责.揭露 Uber 公司的各种黑幕.今天,来自 Uber 公司的司机为您讲述咱「拼车老司机」自己的故事.你以为开着自己的私家车出去满城市的晃悠接客 ...

  6. SQL基础查询实战

    总结: 一.单表查询的情况: 1.where.....group by .. Having count(..) 2.Group by haing min(..)条件and max(..)条件(查询最低 ...

  7. android程序启动画面之Splash总结[转]

    方法一: 很多应用都会有一个启动界面.欢迎画面慢慢隐现,然后慢慢消隐.实现这种效果的方法有两种(暂时只发现两种)1.使用两个Activity,程序启动时候load第一张Activity,然后由tick ...

  8. LeetCode Backpack

    Given n items with size Ai, an integer m denotes the size of a backpack. How full you can fill this ...

  9. Android NDK开发(1)----- Java与C互相调用实例详解

    链接地址:http://www.cnblogs.com/lknlfy/archive/2012/03/13/2394153.html 一.概述 对于大部分应用开发者来说可能都不怎么接触到NDK,但如果 ...

  10. 使用iscroll4可能会遇到的问题(转:记录)

    1.在iscroll4的滚动容器范围内,点击input框.select等表单元素时没有响应这个问题原因在于iscroll需要一直监听用户的touch操作,以便灵敏的做出对应效果,所以它把其余的默认事件 ...