C语言函数指针 和 OC-Block

一、 C语言函数指针

关于函数指针的知识详细可参考:http://www.cnblogs.com/mjios/archive/2013/03/19/2967037.html

#include <stdio.h>
//在main之前定义一个函数
int sum(int a, int b) {
return a + b;
} int main()
{
//定义函数指针变量pfunc,指向sum函数
int (*pfunc)(int a, int b) = sum;
// int (*pfunc)(int, int) = sum;
// int (*pfunc)() = sum;
// int (*pfunc)(int a,int b); pfunc = sum; // 利用指针变量p调用函数
int result = pfunc(, );
//int result = (*pfunc)(1, 3); 也可以 return ;
}

二、OC中block知识

1、什么是Blocks 

     Block是一个C级别的语法以及运行时的一个特性,和标准C中的函数(函数指针)类似,但是其运行需要编译器和运行时支持,从ios4.0开始就很好的支持Block。 

2、在ios开发中,什么情况下使用Block

     Block可以作为类的属性,作为方法的参数,还可以在方法内部定义一个block局部变量,用来保存一段代码。简单来说,block就是一个特殊类型的变量(和变量int a一样),保存一段代码,然后在适当的时候运行,通常用来做并发任务、遍历、以及回调。 

3、直接声明、定义、调用block类型的变量

//
// ViewController.m
// #import "ViewController.h" @implementation ViewController
{
int(^sumBlock)(int x,int y); //声明int(^)(int,int)类型变量sumBlock,block是匿名的函数int (^)(int,int) 有名字的函数int sum(int,int)
} - (void)viewDidLoad {
[super viewDidLoad]; sumBlock = ^int(int x, int y){ //block赋值(定义)
return x+y;
};
} - (void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event {
if(sumBlock) sumBlock(,); //block调用
} @end

4. block的typedefine别名

typedef int(^IntBlock)(int,int);

//给int(^)(int,int)类型取了个别名叫IntBlock,  因为int(^)(int,int)是一种特殊的数据类型:Block,所以typedef语句之后,IntBlock就是一种数据类型,和int/float/double一样。这样使用起来就非常方便。

5.block作为类的属性

//在创建完block的时候需要调用copy的方法。copy会把block从栈上移动到堆上。

@property (copy,nonatomic) int(^sumBlock)(int,int);  //定义了一个int(^)(int,int)类型的属性sumBlock

@property (copy,nonatomic) IntBlock intBlock;           //定义了一个int(^)(int,int)类型的属性intBlock

6.block作为方法参数(形参)的写法

- (void)testBlock:(void (^) ()) aBlock;

- (void)printResult:( int (^) (int, int) )sumBlock;  //此处( int(^)(int, int) )是sumBlock的类型

可见当block作为函数参数时,只是将block类型用()括起来,然后将block名字写在block类型后面而已。

调用方法时,给block类型的形参赋值:

[self printResult:^int(int x, int y) {

return x+y;

}];

[WZCategory  mj_setupReplacedKeyFromPropertyName:^NSDictionary *{

return @{@"ID":@"id"};

}];

7、__block  关键字 

     一个Block内部时可以使用自身作用域外的静态变量(static变量),全局变量(extern变量),__block修饰的自由变量(定义一个变量的时候,如果不加存储修饰符,默认情况下就是自由变量auto,auto变量保存在stack中的。除了auto之外还存在register,static等存储修饰符),对于自由变量,在Block中只读的。 如果想要在block中使用auto变量,需要在自由变量之前加上__block关键字修饰。

三、C语言函数指针 和 OC-Block 对比

1.声明和调用写法对比

int (*CFunc) (int a);        指向函数的指针
 int result = CFunc(10); 
 int (^BFunc)  (int  a);     保存一段代码的block, block是匿名的函数int (^)(int,int)  有名字的函数int sum(int,int)
 int result = BFunc(10);

2. block和函数指针都可以看成是一种数据类型,就像int、float、NSString一样。

3. iOS中将用block定义好的变量看作是一个对象,block对象在作为属性时使用copy关键字。

C语言函数指针 和 OC-Block的更多相关文章

  1. C#委托与C语言函数指针及函数指针数组

    C#委托与C语言函数指针及函数指针数组 在使用C#时总会为委托而感到疑惑,但现在总新温习了一遍C语言后,才真正理解的委托. 其实委托就类似于C/C++里的函数指针,在函数传参时传递的是函数指针,在调用 ...

  2. C语言函数指针基础

    本文写的非常详细,因为我想为初学者建立一个意识模型,来帮助他们理解函数指针的语法和基础.如果你不讨厌事无巨细,请尽情阅读吧. 函数指针虽然在语法上让人有些迷惑,但不失为一种有趣而强大的工具.本文将从C ...

  3. “对外部(局部)变量的访问”是C语言函数指针的最大弱点

    1.“对外部(局部)变量的访问”是C语言函数指针的最大弱点 . #include <stdio.h> #include <stdlib.h> /* 结构体定义 */ struc ...

  4. C语言函数指针实验

    上次看Atmel的示例工程,发现人家使用了函数指针的结构体(函数指针结构体).感叹人家的C语言功夫审核,自己费劲还是只能读懂的份.不过,函数指针确实好用.今天就试试这个超牛的东西.Now let's ...

  5. C语言函数指针的用法

    函数指针是一种在C.C++.D语言.其他类 C 语言和Fortran 2003中的指针.函数指针可以像一般函数一样,用于调用函数.传递参数.在如 C 这样的语言中,通过提供一个简单的选取.执行函数的方 ...

  6. c语言函数指针的理解与使用

    1.函数指针的定义 顾名思义,函数指针就是函数的指针.它是一个指针,指向一个函数.看例子: A) char * (*fun1)(char * p1,char * p2); B) char * *fun ...

  7. C语言函数指针(转载)

    二.通常的函数调用 一个通常的函数调用的例子:/* 自行包含头文件 */void MyFun(int x); /* 此处的声明也可写成:void MyFun(int) */int main(int a ...

  8. C语言函数指针变量和指针函数以及指针数组

    C语言中,一个函数总是占用一段连续的内存区,而函数名就是该函数所占内存区的首地址.我们可以把函数的这个首地址(或称入口地址)赋予一个指针变量,使该指针变量指向该函数.然后通过指针变量就可以找到并调用这 ...

  9. Swift3.0 函数闭包与OC Block

    刚接触Swift,如有不对的点,欢迎指正.转载请说明出处 定义一个基本函数 //定义一个函数,接收一个字符串,返回一个String类型的值 func test(name:String) -> S ...

随机推荐

  1. python Django 路由之正则表达式

    一.路由系统,URL 1. url(r'^index',views.index) #默认的                  url(r'^home',views.Home.as_view()) # ...

  2. python Tensorflow 实现图像的卷积处理

    1.convolution.py import numpy as np from sklearn.datasets import load_sample_images import tensorflo ...

  3. 【转载】MySQL数据库可以用任意ip连接访问的方法

    通过CMD命令行修改数据库表的一个字段的值,实现连接,访问. 第一步.找到MYSQL软件安装所在的bin目录: (1)cd\当前目录 (2)指定MYSQL安装的bin目录 (3)输入 -h local ...

  4. 在Ubuntu 14.04.1 LTS 上安装gettext失败

    使用apt-get install -f,因为有额外的依赖.

  5. Docker 核心概念、安装、端口映射及常用操作命令,详细到令人发指。

    Docker简介 Docker是开源应用容器引擎,轻量级容器技术. 基于Go语言,并遵循Apache2.0协议开源 Docker可以让开发者打包他们的应用以及依赖包到一个轻量级.可移植的容器中,然后发 ...

  6. 在PHP中使用加密技术

    Gpg4win 是一款基于 GPG 的非对称加密软件.非对称加密方式,简单理解就是用公钥加密文件,用私钥解密文件.如果你需要发送加密信息,首先获取接收者的公钥,然后利用该公钥加密后传递,对方利用对应的 ...

  7. 文本(TextView)

    今天给大家介绍一下简单的文本. 首先我们看下TextView的继承关系和一些基本的属性: xml文件如下: <?xml version="1.0" encoding=&quo ...

  8. python基础——Linux系统下的文件目录结构

    单用户操作系统和多用户操作系统 单用户操作系统:指一台计算机在同一时间只能由一个用户使用,一个用户独自享用系统的全部硬件和软件资源. 多用户操作系统:指一台计算机在同一时间可以由多个用户使用,多个用户 ...

  9. 安装SCOM2012在连接数据库时报错:" SQL Server 的安装版本不受支持"

       在SQL群集上有两个实例,分别为:SQLCSNET1\MSSQLSERVER1和SQLCSNET2\MSSQLSERVER2,在计算机sccmz上安装SCOM2012 SP1中的组件 管理服务器 ...

  10. linux邮件客户端mutt日志文件,发不出邮件

    linux上面使用很方便的收发邮件客户端(即MUA),还有一个是mail,大家也可以试试. 在网上找了很多,都说需要msmtp配合使用,其实mutt里面也内建了smtp支持的. mutt and SM ...