C語言不定引數

2021-06-06 13:33:51 字數 2200 閱讀 7617

**:

最近,遇到乙個c語言的不定引數問題。其實,對於c語言的不定引數問題,只需要三個函式就可以搞定了。這三個函式的標頭檔案是,其實下面的三個函式都是乙個巨集定義(macro)。

這三個函式是:

void va_start(va_list ap, last);

type va_arg(va_list ap, type);

void va_end(va_list ap);

如果需要進行其他的一些操作,可以檢視一下man手冊進行查詢。

在這三個函式解釋之前,先看乙個變數va_list,這個變數的型別是什麼呢?通過檢視核心源**,一直追蹤下去,才發現它的型別是void *型別的。

對於va_start(va_list ap, last)函式,這個函式是用來初始化指標變數ap(va_list型別)的,以後處理引數就是預設從ap處開始處理。last一般為char *傳過來引數列表的第乙個引數。

對於va_arg(va_list ap, type)函式來說,就是將ap指標按照type型別向後移動,然後取出ap指標所指的那個引數。

對於va_end(va_list ap)一般和va_start(va_list ap, last)配套使用,做一些善後處理的事情。

這裡有乙個問題,當我們取引數的時候,如何判斷我們要取的引數已經取完了?開始我是這麼想的,通過va_arg的返回值進行判斷,通過查閱資料,都是這麼說的,看來我的猜想是對的。當我把程式寫出來進行測試的時候,發現不是這樣的:

#include

#include

int sum(const int , ...);

int main(void)

int sum(const int first, ...)

va_end(argp);

return sum;

}這個程式的執行結果是:109

86676468

134513824

the result is:141190319

這個結果說明,通過va_arg的返回值進行引數是否取完來判斷是有問題的。

會不會是通過argp的值來判斷的呢?讓我們來做個測試:

#include

#include

int sum(const int , ...);

int main(void)

int sum(const int first, ...)

va_end(argp);

return sum;

}這個程式的執行結果出乎我的意料,出現了段錯誤。

至於如何修改這個程式把不定引數取出來,我還是沒有找到解決方法。後來,我想到了printf()函式,我檢視了它的源**,其中主要是呼叫了vsprintf()函式,至於為什麼呼叫vsprintf()函式,我想可能是為了實現類似於fprintf()之類的函式呼叫的方便,這樣也提高了函式的利用率。printf()函式的主要**:

328 va_start(args, fmt);

329 n = vsprintf(sprint_buf, fmt, args);

330 va_end(args);

想到這裡,我想到了之前看到man手冊中給出的例子為什麼是這樣的:

#include

#include

void

foo(char *fmt, ...)

va_end(ap);

}這裡的話,不是就通過第乙個引數指定之後才讀取的嗎?其實我覺得是間接的告訴了引數的個數。

通過上面的分析,下面做了乙個簡單的不定引數的應用。

問題描述:給定一些字串,求出它們的最長開始字串。

實驗**如下:

#include

#include

#include

#include

void fun(char *fmt, ...);

int main()

void fun(char *fmt, ...)

;int i;

va_start(argp, fmt);

if(*fmt == 's')

fmt++;

while(*fmt)

i++;}}

}va_end(argp);

printf("the result is:%s/n", res);

}程式的執行結果是:

the result is:fan

通過這樣的折騰,就把c語言的不定引數簡單地應用起來了

C語言基礎 不定引數

在這一節裡我們來學習c語言中另外乙個重要的機制,不定引數。不定引數是指函式可以接收不確定個數的引數,不定引數用.來表示,它必須要寫在正常參數列的後面,例如我們熟知的printf函式 int printf char fmt,printf的第乙個引數為char fmt,後面則是不定引數。它表示可以接收任...

C語言不定引數函式

眾所周知,c語言不支援函式過載,支援函式過載的是c 究其原因,c語言在編譯函式之後,將 函式名 存放到函式庫,而c 在編譯函式之後,將 函式名 引數型別 引數型別 存放到函式庫 但是,在查詢fcntl函式時,卻發現其函式原型有多個 int fcntl int fd,int cmd int fcntl...

c語言中的不定引數

在採用c語言程式設計時,函式中的形式引數數目通常是確定的,在呼叫的時候要依次給出與形式引數對應的所有實際引數,但在某些情況下希望函式的引數個數可以根據需要確定,如printf,scanf函式等,c編譯器提供了一系列處理這種情況的巨集,以遮蔽不同的硬體平台造成的差異,增加程式的可移植性,這些巨集包括v...