Что такое автоматическое продвижение типов аргументов переменной функции? - PullRequest
4 голосов
/ 17 августа 2011

Рассмотрим следующий фрагмент кода:

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

void display(int num, ...) {
    char c;
    int j;
    va_list ptr;
    va_start(ptr,num);
    for (j= 1; j <= num; j++){
        c = va_arg(ptr, char);
        printf("%c", c);

    }
    va_end(ptr);
}

int main() {
    display(4, 'A', 'a', 'b', 'c');
    return 0;
}

Программа выдает ошибку времени выполнения, потому что vararg автоматически переводит char в int, и я должен был использовать int в этом случае.

Что всетипы разрешены, когда я использую vararg, как узнать, какой тип использовать, и избежать таких ошибок во время выполнения.

Ответы [ 3 ]

6 голосов
/ 17 августа 2011

еще один случай, о котором другие забыли упомянуть, это типы указателей, в частности, критическим является NULL.Поскольку это может расшириться до 0 или (void*)0 (или некоторых других странных вещей), вы не будете знать, поместит ли компилятор int или void* в список.Поскольку они могут иметь различную ширину, это может привести к досадным ошибкам.

3 голосов
/ 17 августа 2011

Вы можете использовать любой стандартный тип с va_arg, за исключением char, signed char, unsigned char, short, unsigned short, _Bool и float. Возможно, что реализация определяет дополнительные нестандартные типы, которые также имеют целочисленный ранг преобразования ниже, чем int, или аналогично нестандартным маленьким типам с плавающей запятой, но вам не нужно знать об этом, если вы не собираетесь их использовать, поэтому для практических целей цели, список, который я дал, полон.

0 голосов
/ 17 августа 2011

При использовании va_arg char повышается до int.Существуют и другие типы (список, заданный @R ..), которые повышаются.

, поэтому, чтобы прочитать его как char, вы должны выполнить typecast.

, например: c= (char) va_arg (ap, int);

для полного примера см .:

http://en.cppreference.com/w/cpp/language/variadic_arguments

...