• C++ 不定参数(转)


    转自: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将指向某个不包含有效数据的存储单元。

  • 相关阅读:
    初识面向对象
    Git 子模块
    至今为止项目中遇到的问题
    vuex , 简单入(liao)门(jie)
    Git rebase
    Git
    js设计模式工厂模式
    vue slot
    Jquery学习,一道笔试题:关于表格【最近记】
    闭包与this学习
  • 原文地址:https://www.cnblogs.com/litmin/p/7508682.html
Copyright © 2020-2023  润新知