转自:http://www.cnblogs.com/jerrychenfly/archive/2010/10/22/1858232.html

下面,我们来看一下,如果在c++的函数中接收数量不定的函数参数。这种形式如同在C#的函数参数列表中使用params 类型的参数。

  我们可以将函数定义成能够接受任意数量的实参。通过将省略号(3个句点...)写在函数定义中形参列表的最后,即可表示调用该函数时可以提供数量可变的实参。例如:

  int sumValues(int first,...)

  {

    //Code for the function

  }

  函数定义中必须至少有一个普通形参,但也可以有多个。省略号必须总是放在形参列表的最后。

  显然,定义中没有关于可变列表中实参的类型或数量的任何信息,因此我们的函数代码必须弄清楚自己被调用时接收的是什么。本地C++库在stdarg.h头文件中定义了va_start、va_arg、和va_end宏,以帮助我们做这件事。用示例来说明其用法是最容易的。

  

  

  #include <iostream>
  #include "stdarg.h"

  using namespace std;

  int sum(int count,...)
  {
     if(count<=0)
        return 0;
     va_list arg_ptr;
     va_start(arg_ptr,count);

    int sum = 0;
     for (int i=0;i<count;i++)
     {
        sum+=va_arg(arg_ptr,int);
     }
     va_end(arg_ptr);
     return sum;
    }

  int main()
  {

    cout<<sum(2,4,6,8,10,12)<<endl;
     cout<<sum(2,22,33,44,55,66,77,88,99)<<endl;
     return 0;
  }

  本例结果:

    10

    55

    按任意键继续。。。

  示例说明

   main()函数函数在两条输出语句中调用了sum()函数,第一次有6个实参,第二次有9个实参。

  sum()函数有一个int类型的普通形参,它表示后面跟着的实参的数量。形参列表中的省略号表明可以传递任意数量的实参。基本上,我们有两种方法来确定调用该函数时有多少实参:第一是像sum()函数一样,用某个固定的形参指定实参的数量;第二是要求最后一个实参具有特殊的标记值,以便我们进行检查和确认。

  为了开始处理可变的实参列表,我们首先声明一个va_list类型的指针:

  va_list arg_ptr;

  va_list 类型是在stdarg.h头文件中定义的,该指针用来依次指向各个实参。

  va_start宏用来初始化arg_ptr,使其指向列表中的第一个实参:

  va_start宏用来初始化arg_ptr,使其指向列表中的第一个实参:

  va_start(arg_ptr,count);

  这个宏的第二个实参是函数形参列表中活力号前面固定形参的名称,用来确定第一个可变实参的位置。

  我们在for循环中取出列表中各个实参的值:

  for (int i=0;i<count;i++)
   {
      sum+=va_arg(arg_ptr,int);
   }

  var_arg宏返回arg_ptr指向的位置存储的实参值,并使arg_ptr递增,以指向下一个实参值。va_arg宏的第二个实参是第一个实参的类型,决定着我们得到的数值以及va_arg递增的方式,因此如果该实参不正确,将造成混乱。程序也许会执行,但我们得到的数值将是无用数据,而且arg_ptr将被错误地递增,从而指向另外的无用数据。

  当结束检索实参值之后,我们用下面这条语句使arg_ptr复位:

  va_end(arg_ptr);

  va_end宏将我们传递给它的实参--va_list类型的指针复位成空值。始终这样做是个好主意,因为在处理过实参之后,arg_ptr将指向某个不包含有效数据的存储单元。

C++ 不定参数(转)的更多相关文章

  1. golang中不定参数与数组切片的区别

    package main import "fmt" func main() { myfunc1(, , , ) //传递不定数量的参数 myfunc2([], , , }) //传 ...

  2. 深入浅出ES6(五):不定参数和默认参数

    作者 Jason Orendorff  github主页  https://github.com/jorendorff 不定参数 我们通常使用可变参函数来构造API,可变参函数可接受任意数量的参数.例 ...

  3. C技巧:结构体参数转成不定参数

    下面这段程序是一个C语言的小技巧,其展示了如何把一个参数为结构体的函数转成一个可变参数的函数,其中用到了宏和内建宏"__VA_ARGS__",下面这段程序可以在GCC下正常编译通过 ...

  4. 不定参数函数原理以及实现一个属于自己的printf函数

    一.不定参数函数原理 二.实现一个属于自己的printf函数 参考博文:王爽汇编语言综合研究-函数如何接收不定数量的参数

  5. C语言函数不定参数实现方式

    函数如何实现不定参数: 由于在C语言中没有函数重载,解决不定数目函数参数问题变得比较麻烦,即使采用C++,如果参数个数不能确定,也很难采用函数重载.对这种情况,提出了指针参数来解决问题. (1)va_ ...

  6. [js高手之路] es6系列教程 - 不定参数与展开运算符(...)

    三个点(...)在es6中,有两个含义: 用在形参中, 表示传递给他的参数集合, 类似于arguments, 叫不定参数. 语法格式:  在形参面前加三个点( ... ) 用在数组前面,可以把数组的值 ...

  7. SE6 不定参数和默认参数详解和使用细节

    在SE5以前我们通常通过arguments类数组对象来引用不定形参,SE6则使用了一种叫做不定参数的写法,比起隐式的arguments要直观的多. 不定参数使用...参数名来指定一个不定参数,参数名指 ...

  8. dataframe的select传入不定参数

    在提取 dataframe 里面的列时,需要传入不定参数,即 dataframe.select(args) .例如某个 dataframe 如下: 一般提取某列或者某几列的时候是这样子写的: data ...

  9. 不定参数对arguments对象的影响

    如果声明函数时定义了不定参数,则在函数被调用时,arguments对象包含了所有传入的参数: function checkArgs(...args){ console.log(args.length, ...

  10. 深入浅出ES6:不定参数和默认参数

    不定参数 我们通常使用可变参函数来构造API,可变参函数可接受任意数量的参数.例如,String.prototype.concat方法就可以接受任意数量的字符串参数.ES6提供了一种编写可变参函数的新 ...

随机推荐

  1. 文件上传之伪Ajax方式上传

    From: <由 Windows Internet Explorer 8 保存> Subject: =?gb2312?B?zsS8/snPtKvWrs6xQWpheLe9yr3Jz7SrI ...

  2. MyBatis小抄

    持续更新中. Every MyBatis application centers around an instance of SqlSessionFactory A cleaner approch t ...

  3. springMVC(5)---导入excel文件数据到数据库

    springMVC(5)---导入excel文件数据到数据库 上一篇文章写了从数据库导出数据到excel文件,这篇文章悄悄相反,写的是导入excel文件数据到数据库.上一篇链接:springMVC(4 ...

  4. Anaconda系统中管理程序包(Package)

    列出所有已安装的程序包 conda list 在已安装的程序包中查找某个特定的程序包 conda search package-name 安装程序包 conda install beautiful-s ...

  5. 给yii架构的网站做Android客户端

    网站未预留接口.给这类网站制作客户端就是模拟网页发送的post和get请求,然后获取服务器返回的数据. 1.在做客户端时先使用httpwatch分析浏览器发送的get和post请求的内容和URL.分析 ...

  6. 对DataTable(或者DataSet)修改后,提交修改到数据库

    http://blog.csdn.net/nidexuanzhe/article/details/8228832 说明:通常我们在做数据库交互时,并不一定要使用特定的SQL语句来更新数据,.NET F ...

  7. Asp.net IIS Express 无法启动 解决办法

    http://www.mamicode.com/info-detail-1893424.html 一 .其他项目都可以,就这么一个不行 用记事本或者其他什么文本编辑器,打开项目的.csproj文件,定 ...

  8. HY.Mail:C#简单、易用的邮件工具库

    一.开发HY.Mail的初衷 Nuget或者github上有很多成熟且优秀的邮件库可以使用, 但是目前找到的使用都不够简洁或者不适合我的使用场景 我的场景是开发应用场景(例如系统通知.运维通知),而非 ...

  9. robotframework的学习笔记(十四)------学习Robot Framework必须掌握的库—-BuiltIn库

    作为一门表格语言,为了保持简单的结构,RF没有像别的高级语言那样提供类似if else while等内置关键字来实现各种逻辑功能,而是提供给了用户BuiltIn库.如果用户想在测试用例中实现比较复杂的 ...

  10. LNMP架构之搭建wordpress博客网站

    系统环境版本 [root@db02 ~]# cat /etc/redhat-release CentOS release 6.9 (Final) [root@db02 ~]# uname -a Lin ...