1.可變參數產生原因
首先來看一個簡單的例子。
int Add(int x, int y)
{return x + y;
}
int main()
{int sum = 0;sum = Add(1, 2);//sum = Add(1, 2, 3);//sum = Add(1);system("pause");return 0;
}
我們可以看到,對于這個代碼只可以計算兩個數的加法。
這樣我們引入一個新的知識點!
可變參數實現求任意數的和
#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#include <stdarg.h>
#include <stdlib.h>int Add(int num, ...)
{int sum = 0;va_list arg;va_start(arg, num);for (int i = 0; i < num; i++){sum += va_arg(arg, int);}va_end(arg);return sum;
}
int main()
{printf("%d\n", Add(4, 2, 3, 4, 5));system("pause");return 0;
}
詳解
1.main()函數第一句
printf("%d\n", Add(4, 2, 3, 4, 5));
第一個4表示元素個數剩余表示元素內容
2.
操作符的含義:
1.
va_list arg;
宏操作符 | 實際含義 | 詳解 |
---|---|---|
va_list | char * | va_list arg 創建一個字符指針arg,用于訪問參數列表的未確定部分。 |
2.
va_start(arg, num);
(ap=(va_list)&v + _INTSIZEOF(v))
宏操作符 | 實際含義 | 詳解 |
---|---|---|
va_start (ap,v) | (ap=(va_list)&v + _INTSIZEOF(v)) | 初始化變量arg ,va_start有兩個參數,它的第一個參數是va_list所創建的字符指針。第2個參數是“…”之前的那個參數;(不可以讀省略號) |
va_start (arg,num) | (arg=(char *)&v + _INTSIZEOF(num)) | |
_INTSIZEOF | (sizeof(n) + sizeof(int)-1 & ~(sizeof(int)-1) | 跳過num,來到位置參數的第一個參數。向上取四的整數倍 |
3.
for (int i = 0; i < num; i++){sum += va_arg(arg, int);}
宏操作符 | 實際含義 | 詳解 |
---|---|---|
va_arg(ap,t) | (*(t*)((ap += _INTSIZEOF(t)) - _INTSIZEOF(t))) | (*(t*)((arg += _INTSIZEOF(int)) - _INTSIZEOF(int))) |
(*(t*)((arg += _INTSIZEOF(int)) - _INTSIZEOF(int))) | (*(int *)((arg += 4) - 4)) | |
(arg += 4) - 4) | arg; arg+=4; | 先給arg加4再減,arg這次產生的結果沒變,但是arg指向了下一個位置。一個代碼做了兩個動作 |
for (int i = 0; i < num; i++){sum += va_arg(arg, int);}
取出所有未知參數,然后加給sum
宏操作符 | 實際含義 | 詳解 |
---|---|---|
va_end(ap) | (ap = (va_list)0) | 給指針賦值空指針。不用的時候釋放 |
va_end(arg);
防止指針亂指用完一定要釋放。