block的用法和数组排序(高级)

一, block

我们都知道函数只可以嵌套调用,但决不允许函数的嵌套定义,这有时给我们带来了很大的不便,而OC提供的block用法为我们解决了这个问题,下面简单说一下1,block的用法:

(1)block是用来存储函数,所以给block赋值时赋的是整个函数的实现,例如,要在main函数里写一个求两个数的和的函数,返回值为整型,参数为两个整型,通常在函数外面会这样写

int sum(int x, int y)

{

return x + y;

}

如果要在函数内部写就需要用到block语句写法如下:

int (^sum)(int x,int y) = ^(int x, int y)

{

return x + y;

};

block 变量的类型是: int (^)(int x,int y) (这里的”(^)”是系统规定的block写法) sum是block变量的名字, "="号右边的

^(int x, int y)

{

return x + y;

};

是block变量的初始值,

当把函数的实现赋给block后,block变量sum就可以当做函数名使用

如: NSLog(@"sum = %d",sum (5,10));

从block的定义可以看出它跟函数指针的定义很相似,唯一不同就是函数指针的类型定义时是用(*),而block是用(^).

(2),此外当在block外面定义了变量(局部变量),如果没有在变量前加上"__block"修饰,则在block内部无法对该变量修改,在block内部系统识别该变量是readonly不可修改的,如果要修改block外边的变量,必须将该变量用"__block"修饰.block外部的局部变量被"__block"修饰后在block内部告诉编译器不要再把该变量当做常量来看待,但是若在block内部访问全局变量,则不需要用__block修饰,有关全局变量下面可以再详细的叙述一下;

(3), 如果使用block时对它的定义感觉麻烦,我们也可以使用typedef对它的类型重定义 如: typedefint(^BLOCK) (int x, int y);这样如果再定义该类型的block,只需要使用BLOCK代替int (^)(int x,int y)即可.

(4), 对于全局变量:在一个文件里定义了一个全局变量例如:(int a = 10;),如果在其他文件里想用该变量a(如果在main函数里也定义了int a,则编译时会失败,因为系统编译的时.m文件,而main函数也是.m文件,在同样的.m文件里同时出现两个变量名相同的变量,系统是不允许的),则需要在要调用该变量的文件里声明一下即用 externint a;他会告诉编译器,这个变量a已经在其他文件里定义了. 如果在每个文件了都定义了同一个名的变量,又只想在本文件里使用,需要给变量声明为static即定义为静态变量(此时系统识别变量是以static int去找到地址取出其中的数据的).

二,     数组排序

1,首先建立一个人类

在.h文件里定义实例变量和方法声明

{

NSString *_name; //姓名

CGFloat _height; //身高

NSInteger _age; //年龄

}

//初始化

- (id)initWithname:(NSString *)name age:(NSInteger)age height:(CGFloat)height;

//setter

- (void)setName:(NSString *)name;

- (void)setHeight:(CGFloat)height;

- (void)setAge:(NSInteger)age;

//getter

- (NSString *)name;

- (CGFloat)height;

- (NSInteger)age;

在.m文件里

//setter

- (void)setName:(NSString *)name

{

_name = name;

}

- (void)setHeight:(CGFloat)height

{

_height = height;

}

- (void)setAge:(NSInteger)age

{

_age = age;

}

//getter

- (NSString *)name

{

return_name;

}

- (CGFloat)height

{

return_height;

}

- (NSInteger)age

{

return_age;

}

#pragma mark - override method

//重写description

- (NSString *)description

{

return  [NSStringstringWithFormat:@"name = %@, age = %ld,height = %.2f",_name,_age,_height];

}

#pragma mark - initmethod

- (id)initWithname:(NSString *)name age:(NSInteger)age height:(CGFloat)height

{

self = [superinit];

if (self != nil) {

_name = name;

_age = age;

_height = height;

}

returnself;

}

我们在main函数内创建几个人类的对象,用一个数组personArr存储

Person *per1 = [[Personalloc] initWithname:@"Frank"age:20height:175];

Person *per2 = [[Personalloc] initWithname:@"Duke"age:25height:170];

Person *per3 = [[Personalloc] initWithname:@"Lili"age:22height:165];

Person *per4 = [[Personalloc] initWithname:@"Mary"age:18height:160];

存储对象

NSArray *personArr = [[NSArrayalloc] initWithObjects:per1,per2,per3,per4, nil];

若想为人分别按照年龄,身高升序排序,按照姓名降序排序,则需要添加方法,如下:

//添加比较的方法 compare

//按年龄升序排序

-  (NSComparisonResult)personAge:(Person *)anotherPerson;

-

//按身高升序排序

-  (NSComparisonResult)personHeight:(Person *)anotherPerson;

//按姓名降序排序

- (NSComparisonResult)personNameDescending:(Person *)anotherPerson;

在.m文件对方法实现:

//按年龄升序排序

- (NSComparisonResult)personAge:(Person *)anotherPerson

{

if ([selfage] > [anotherPerson age]) {

returnNSOrderedDescending; //1

} elseif ([selfage] == [anotherPerson age])

{

returnNSOrderedSame; //0

} else {

returnNSOrderedAscending; //-1

}

}

//按身高升序排序

- (NSComparisonResult)personHeight:(Person *)anotherPerson

{

if ([selfheight] > [anotherPerson height]) {

returnNSOrderedDescending; //1

} elseif ([selfheight] == [anotherPerson height])

{

returnNSOrderedSame; //0

} else {

returnNSOrderedAscending; //-1

}

}

//按姓名降序排序

- (NSComparisonResult)personNameDescending:(Person *)anotherPerson

{

return -[[selfname] compare:[anotherPerson name]];

}

在main函数中调用

//对数组元素按年龄升序排序

NSArray *sortAge = [personArr sortedArrayUsingSelector:@selector(personAge:)];

NSLog(@"%@",sortAge);

//对数组元素按身高升序排序

NSArray *sortHeight = [personArrsortedArrayUsingSelector:@selector(personHeight:)];

NSLog(@"%@",sortHeight);

//对数组元素按姓名序排序

NSArray *sortNameDe = [personArrsortedArrayUsingSelector:@selector(personNameDescending:)];

NSLog(@"%@",sortNameDe);

三,对数组的元素降序排序和升序排序

NSArray *arr = [[NSArrayalloc] initWithObjects:@"ff",@"bb",@"aa",@"dd", nil];

对数组元素升序排序

NSArray *sortArrAscending = [arrsortedArrayUsingSelector:@selector(compare:)];

NSLog(@"%@",sortArrAscending);

//对数组元素降序排序

//通过block排序

NSArray *sortAscending = [arr sortedArrayUsingComparator:^NSComparisonResult(id obj1, id obj2) {

//对block匿名函数实现比较方法

//1)将id类型转为NSString *类型

NSString *str1 = (NSString *)obj1;

NSString *str2 = (NSString *)obj2;

//字符串比较

return -[str1 compare:str2];

}];

NSLog(@"%@",sortAscending);

综上所述:

(1),sortedArrayUsingSelector:排序适用于升序排序以及自定义的类排序

(2),block(sortedArrayUsingComparator:^NSComparisonResult(id obj1, id obj2))排序方式适用于当数组中的对象类型是系统类型(即系统提供的OC类型)时,并且要降序排序时

系统提供的排序方法sortedArrayUsingSelector:还是利用冒泡排序法,只是把 if 里的(compare)判断条件中的要比较的对象空出来了,大于零的条件(return 1)已经给定,也就是按照升序排序,如果前者大于后者,则交换位置

系统提供的排序方法sortedArrayUsingComparator:^NSComparisonResult(idobj1, id obj2)也是利用冒泡排序法,它跟sortedArrayUsingSelector:不同,他把if 里的判断条件中的要比较的对象类型让我们自己选择,既可以是任何对象类型, obj1和obj2就是让我们自己选择的,大于零的条件已经给定,但是 > 0的返回值也让我们自己选择,也就是按照升序或者降序排序有我们自己决定,如果降序排序,则返回值为-1,若为升序返回值为1;

block的用法和数组排序(高级)

时间: 2024-10-13 02:24:27

block的用法和数组排序(高级)的相关文章

block的用法和循环引用

一.block在OC中的用法可以分为大概一下几种. 1>用于成员属性,保存一段代码,可以替代代理传值. 比如说,创建一个ViewController控制器,点击屏幕就跳转到ModalViewController控制器里的时候,不用代理用block实现一些功能: // 在ModalViewController.h文件里声明: @property (nonatomic, strong) void(^valueBlock)(NSString *data); //在ModalViewController

Runtime 、 Block

1 使用Block方式,对学生对象进行排序. 1.1 问题 在iOS4.0+ 和Mac OS X 10.6+ 中添加了Block概念,以对C语言进行扩展.在Block中可以定义参数列表.返回类型,还可以获取被定义在的作用域内的局部变量的值,并且能修改使用__block修饰的局部变量的值. Block本质上是一个变量,该变量中存储的数据是一段函数体. 1.2 方案 本案例要求定义一个学生类TRSTudent,然后创建该类的三个对象.用这三个对象建立一个数组,使用Block变量对这个数组排序.并将排

iOS中block的用法 以及和函数用法的区别

ios中block的用法和函数的用法大致相同 但是block的用法的灵活性更高: 不带参数的block: void ^(MyBlock)() = ^{}; 调用的时候  MyBlock(); 带参数的block: int ^(MyBlock)(int,int) = ^(int a,int b){return a+b;} 调用MyBlock(5,6); 将block当作某个类的属性的写法 typedef void (^BlockOption)(); @property (nonatomic,ass

OC语言的特性(二)-Block

本篇文章的主要内容 了解何谓block. 了解block的使用方法. Block 是iOS在4.0版本之后新增的程序语法. 在iOS SDK 4.0之后,Block几乎出现在所有新版的API之中,换句话说,如果不了解Block这个概念就无法使用SDK 4.0版本以后的新功能,因此虽然Block本身的语法有点难度,但为了使用iOS的新功能我们还是得硬着头皮去了解这个新的程序概念. 一.看一看什么是Block 我们使用'^'运算符来声明一个Block变量,而且在声明完一个Block变量后要像声明普通

ios block初级使用

block和GCD是ios高级程序员面试必问的问题,本篇先介绍下block 第一部分:概述 Block是一个C级别的语法以及运行时的一个特性,和标准C中的函数(函数指针)类似,但是其运行需要编译器和运行时支持,从ios4.0开始就很好的支持Block,个人感觉使用block最大的便利就是简化的回调过程,以前使用uiview的动画,进程要控制动画结束后进行相应的处理,ios4.0之后,uiview新增了对block的支持,现在只要使用简单的一个block代码就可以在写动画的代码部分直接添加动画结束

Objective-C中的Block(闭包)

学习OC有接触到一个新词Block(个人感觉又是一个牛气冲天的词),但不是新的概念,不是新的东西.学过Javascript的小伙伴对闭包应该不陌生吧~学过PHP的应该也不陌生,在PHP5.3版本以后也支持闭包, 也就是OC中所提到的Block. 到底什么是闭包或者block呢?用大白话说就是匿名函数,也就是在函数中可以包含这函数.就是在函数中可以定义匿名函数然后在函数中调用.学习OC中的block之前也小担心一下,Block在OC中属于高级的部分,心里有又有个疑问:学起来难不难?看过Block的

Objective-C中 Block 在iOS在4.0版本的使用

了解何谓block. 了解block的使用方法. Block 是iOS在4.0版本之后新增的程序语法. 在iOS SDK 4.0之后,Block几乎出现在所有新版的API之中,换句话说,如果不了解Block这个概念就无法使用SDK 4.0版本以后的新功能,因此虽然Block本身的语法有点难度,但为了使用iOS的新功能我们还是得硬着头皮去了解这个新的程序概念. 一.看一看什么是Block 我们使用'^'运算符来声明一个Block变量,而且在声明完一个Block变量后要像声明普通变量一样,最后要加'

OC6-block-函数指针

目标: 1.通过类中的方法进行排序 2block-函数指针, 3.通过block实现数组的排序 1.自定义类在数组中的排序: (1)在自定义类中声明实现一个方法,方法的返回值是bool类型,意思是是否进行元素的交换 (2)在main中调用这个方法 (3)在数组中,@selecter 是方法选择器,在指定的对象中,寻找指定的方法. 返回值是布尔类型,判断是否交换,必须有且只有一个参数. 参数的类型是自身类型,参数的代表的是它在数组中的下一个元素. //    [arr1 sortedArrayUs

15.Object-C--NSArray数组的排序

NSArray数组的排序有三种方式: 1.简单排序(sortedArrayUsingSelector:) 2.利用block语法(sortedArrayUsingComparator:) 3.高级排序(sortedArrayUsingDescriptors:) 1.简单排序(sortedArrayUsingSelector:) 如果只是对字符串的排序,可以利用sortedArrayUsingSelector:方法就可以了,代码如下: 1 #pragma mark 数组排序 sortedArray