日本免费高清视频-国产福利视频导航-黄色在线播放国产-天天操天天操天天操天天操|www.shdianci.com

學無先后,達者為師

網站首頁 編程語言 正文

C語言中不定參數?...?的語法以及函數封裝_C 語言

作者:錦天 ? 更新時間: 2023-03-22 編程語言

Intro

有一天看C代碼看到某個方法有這樣的定義:在函數形參列表處,有...的寫法,就像Java中的不定參數那樣。
如:

int	 printf(const char * __restrict, ...) __printflike(1, 2);
int	 scanf(const char * __restrict, ...) __scanflike(1, 2);

那么C語言中的不定參數特性,是怎樣使用的呢,以及我們如何利用該特性,封裝自己的函數?

語法測試

依賴庫

需要用到 stdarg.h 中的三個函數:

#define va_start(ap, param) __builtin_va_start(ap, param)
#define va_end(ap)          __builtin_va_end(ap)
#define va_arg(ap, type)    __builtin_va_arg(ap, type)

新函數使用測試:遍歷并打印不定參數中的值

主要是測試一下上面提到的三個庫函數的使用。

#include <stdio.h>
#include <stdarg.h>

// 聲明列表的結束值
#define ARGUMENTS_END_VALUE -1

void printMultiArgs(int firstArgs, ...) {

    // 聲明參數列表的變量
    va_list ap;
    
    // 初始化參數列表
    va_start(ap, firstArgs);
    printf("%d\n", firstArgs);
    
    int currValue;
    while ((currValue = va_arg(ap, int)) != ARGUMENTS_END_VALUE) {
        printf("%d\n", currValue);
    }

    // 結束參數列表
    va_end(ap);
}

int main(int argc, const char * argv[]) {
    printMultiArgs(1,2,3,4,5,6,7,8,9, ARGUMENTS_END_VALUE);
    return 0;
}

用兩種方式封裝函數:對多個int值求和

//
//  main.c
//  C不定參數
//
//  Created by wuyujin1997 on 2023/1/23.
//

//#define va_start(ap, param) __builtin_va_start(ap, param)
//#define va_end(ap)          __builtin_va_end(ap)
//#define va_arg(ap, type)    __builtin_va_arg(ap, type)

#include <stdio.h>
#include <stdarg.h>

// 聲明列表的結束值
#define ARGUMENTS_END_VALUE -1

void printMultiArgs(int firstArgs, ...) {

    // 聲明參數列表的變量
    va_list ap;
    // 初始化參數列表
    va_start(ap, firstArgs);
    printf("%d\n", firstArgs);
    
    int currValue;
    while ((currValue = va_arg(ap, int)) != ARGUMENTS_END_VALUE) {
        printf("%d\n", currValue);
    }

    // 結束參數列表
    va_end(ap);
}


/// 對多個int變量求和(需要提前約定好參數結束的標志值 ARGUMENTS_END_VALUE)
/// - Parameter firstArgs: <#firstArgs description#>
int sum1(int firstArgs, ...) {
    int result = 0;
    
    va_list ap;
    va_start(ap, firstArgs);
    result+= firstArgs; // 手動處理第一個參數
    int currValue;
    while ((currValue = va_arg(ap, int)) != ARGUMENTS_END_VALUE) {
        result += currValue;
    }
    va_end(ap);
    
    return result;
}


/// 對多個int變量求和(需要主動本方法:不定參數的個數是多少)
/// - Parameters:
///   - count: 不定參數的個數
///   - firstArgs: 第一個參數,顯式的形參
int sum2(int count, int firstArgs, ...) {
    int result = 0;
    
    va_list ap;
    va_start(ap, firstArgs);
    result += firstArgs;
    for (int i = 1; i < count; i++) {
        int currValue = va_arg(ap, int);
//        printf("%d  %d\n", i, currValue);
        result += currValue;
    }
    va_end(ap);
    
    return result;
}

int main(int argc, const char * argv[]) {

    printMultiArgs(1,2,3,4,5,6,7,8,9, ARGUMENTS_END_VALUE);
    printf("sum1  %d\n", sum1(1,2,3,4,5,6,7,8,9, ARGUMENTS_END_VALUE));
    int LENGTH = 9;
    printf("sum2  %d\n", sum2(LENGTH, 1,2,3,4,5,6,7,8,9, ARGUMENTS_END_VALUE));

    return 0;
}

執行結果:

總結

  • 需要引入頭文件 #include <stdarg.h>
  • 一個新類型,三個新函數
    • 類型 va_list
    • 函數,其中 ap 為 va_list 類型的變量。
      • va_start(ap, param) param為不定參數列表的第一個參數。
      • va_arg(ap, type) 不定參數中變量的類型嗎,如int, short, long 等。
      • va_end(ap)
  • 如何確定 va_arg 的size/有多少個元素? 沒有原生的屬性/變量可以告訴我們。
    • 約定一個值作為 end_value ,而且要保證:這個值不會出現在傳入的多個參數值中。
    • 在咱自己封裝的函數中,新增一個參數用于告知被調函數內部:本次不定參數的size是多少。
  • 注意不定參數的類型匹配。

總結?

原文鏈接:https://blog.csdn.net/wuyujin1997/article/details/128752337

欄目分類
最近更新