简介

一个可变参数函数是指一个函数拥有不定的参数,即为一个函数可接收多个参数。有时我们会遇到一些算术问题需要用到,比如是计算传入参数的总和,字符串的连接或是其它操作过程,我们在 OC 里也经常使用,最经典的就是 NSLog( C 为 printf ) ,它可以指定格式的输出,格式化输出的内容。

现在我们先来看看普通函数的定义方法。

普通函数

一般我们定义的函数都是指定有多少个参数,如果是有三个参数,我们可以这样写。

- (void)exampleObj:(NSString *)obj obj2:(NSString *)obj2 obj3:(NSString *)obj3
{ }

这样有一个问题,如果我们需要计算值,比如需要计算5个或10个数值相加的运行,那我们在函数里是不是需要定义5个或10个的参数?如果有100个数值需要计算 …… 。

可变参数函数

现在,我们可以通过定义 可变参数函数 去实现刚刚的问题,比如我们现在需要传进来参数的数值之和,而且传的参数个数是不固定的。可变参数函数的定义方法很简单,我们在参数的后面加上 ", ..."就可以了,例如。

- (void)exampleObj:(NSString *)obj obj2:(NSString *)obj2 obj3:(NSString *)obj3, ...
{ }

现在,我们回到刚刚的难题,这个函数主要是用来计算用户传进来的数值之和。

- (int)sum:(int)num, ...
{
int result = num;
int objNum; va_list arg_list;
va_start(arg_list, num);
while ((objNum = va_arg(arg_list, int))) {
result += objNum;
}
va_end(arg_list);
return result;
}

va_list:用来保存宏 va_start 、va_arg 和 va_end 所需信息的一种类型。为了访问变长参数列表中的参数,必须声明 va_list 类型的一个对象。

va_start:访问变长参数列表中的参数之前使用的宏,它初始化用 va_list 声明的对象,初始化结果供宏va_arg和va_end使用;

va_arg:展开成一个表达式的宏,该表达式具有变长参数列表中下一个参数的值和类型。每次调用 va_arg 都会修改,用 va_list 声明的对象从而使该对象指向参数列表中的下一个参数。

va_end:该宏使程序能够从变长参数列表用宏 va_start 引用的函数中正常返回。

使用方法

使用方法也很简单,在可变参数里,所有参数均用逗号隔开。

NSLog(@"%d", [self sum:, , nil]);

注意事项

使用的时候,可变参后最后面加一个nil值,这样是代表结束的意思。就像UIAlertView初始化的那样,它一开始不知道你有多少个Button,你可以自由地往里加Button,最后也是由一个nil结束,所以两个是一样的道理。

注意点

1)当我们要创建一个可变参数函数时,必须把省略号( ... )放到参数列表后面,同时也只能拥有一个这样的格式,因为我们不能定义两个可变的参数。

2)当我们需要读取 可变参数列表 时,必须先指定一个变数 va_list ,然后使用宏 va_start 、va_arg、va_end 来获取。

参考:

C可变参数函数 实现 —— http://blog.csdn.net/weiwangchao_/article/details/4857567

维基百科.可變參數函數 —— http://zh.wikipedia.org/wiki/可變參數函數


博文作者:GarveyCalvin

博文出处:http://www.cnblogs.com/GarveyCalvin/

本文版权归作者和博客园共有,欢迎转载,但须保留此段声明,并给出原文链接,谢谢合作!

ios开发-Object-C可变参数函数的更多相关文章

  1. Swift开发第十篇——可变参数函数&初始化方法顺序

    本篇分为两部分: 一.Swift中的可变参数函数 二.初始化方法的顺序 一.Swift中的可变参数函数 可变参数函数指的是可以接受任意多个参数的函数,在 OC 中,拼接字符串的函数就属于可变参数函数 ...

  2. C语言可变参数函数的编写

    1. 引言 C语言我们接触的第一个库函数是 printf(“hello,world!”);其参数个数为1个. 然后,我们会接触到诸如: printf(“a=%d,b=%s,c=%c”,a,b,c);此 ...

  3. 通过Java发射机制调用可变参数函数

    1.获取可变参数的函数       获取可变参数的函数与获取参数类型为数组类型一样. clazz.getMethod("test", Object[].class);    其中O ...

  4. C语言学习020:可变参数函数

    顾名思义,可变参数函数就是参数数量可变的函数,即函数的参数数量是不确定的,比如方法getnumbertotal()我们即可以传递一个参数,也可以传递5个.6个参数 #include <stdio ...

  5. C语言中可变参数函数实现原理

    C函数调用的栈结构 可变参数函数的实现与函数调用的栈结构密切相关,正常情况下C的函数参数入栈规则为__stdcall, 它是从右到左的,即函数中的最右边的参数最先入栈.例如,对于函数: void fu ...

  6. C可变参数函数 实现

    转自:http://blog.csdn.net/weiwangchao_/article/details/4857567 C函数要在程序中用到以下这些宏: void va_start( va_list ...

  7. C语言可变参数函数实现原理

    一.可变参数函数实现原理 C函数调用的栈结构: 可变参数函数的实现与函数调用的栈结构密切相关,正常情况下C的函数参数入栈规则为__stdcall, 它是从右到左的,即函数中的最右边的参数最先入栈. 本 ...

  8. c可变参数函数

    C函数要在程序中用到以下这些宏: <pre lang="c" escaped="true">void va_start( va_list arg_p ...

  9. 【转】C/C++中可变参数函数的实现

    转自:http://www.cnblogs.com/cylee025/archive/2011/05/23/2054792.html 在C语言的stdarg.h头文件中提供了三个函数va_start, ...

随机推荐

  1. 使用sklearn进行交叉验证

    模型评估方法 假如我们有一个带标签的数据集D,我们如何选择最优的模型? 衡量模型好坏的标准是看这个模型在新的数据集上面表现的如何,也就是看它的泛化误差.因为实际的数据没有标签,所以泛化误差是不可能直接 ...

  2. AR(Average Recall, 平均查全率), ANMRR(Average Normalized Modified Retrieval Rate, 平均归一化检索秩)

    AR(Average Recall, 平均查全率), ANMRR(Average Normalized Modified Retrieval Rate, 平均归一化检索秩)

  3. 在pcDuino上使用蓝牙耳机玩转音乐

    1.资源 pcDuino板子一个.HDMI to VGA线一条.电源线一条.USB hub一个.显示器.鼠标.键盘.蓝牙适配器.蓝牙耳机. 2.资源已经到位,让我们开始吧 1.在ubuntu上安装蓝牙 ...

  4. Django Pagination

    Django provides a few classes that help you manage paginated data – that is, data that’s split acros ...

  5. C#各种结束进程的方法详细介绍

    Process类的CloseMainWindow, Kill, Close Process.CloseMainWindow是GUI程序的最友好结束方式,从名字上就可以看出来它是通过结束主窗体,相当于用 ...

  6. 《Java虚拟机原理图解》3、JVM执行时数据区

    [last updated :2014/11/7]     JVM执行时数据区(JVM Runtime Area)事实上就是指JVM在执行期间,其对计算机内存空间的划分和分配.本文将通过下面几个话题来 ...

  7. 使用Jacob与Word文件交互

    转自:http://www.blogjava.net/lonsy/archive/2009/01/09/250713.html Jacob项目的官方地址: Http://sourceforge.net ...

  8. (原创)2. WPF中的依赖属性之二

    1 依赖属性 1.1 依赖属性最终值的选用 WPF属性系统对依赖属性操作的基本步骤如下: 第一,确定Base Value,对同一个属性的赋值可能发生在很多地方.还用Button的宽度来进行举例,可能在 ...

  9. php 验证身份证号码

    身份证号码的结构 身份证号码是特征组合码,由17位数字本体码和一位校验码组成. 排列顺序从左至右依此为:六位数字地址码,八位数字出生日期码,三位数字顺序码和一位数字校验码. 地址码(前六位数) 表示编 ...

  10. Spark Streaming中空batches处理的两种方法(转)

    原文链接:Spark Streaming中空batches处理的两种方法 Spark Streaming是近实时(near real time)的小批处理系统.对给定的时间间隔(interval),S ...