2013-02-24 4 views
5

У меня есть следующая функция C с переменным числом аргументов, который должен искать char* word через хэш-таблицу и написать true или false в файле, который, если указано, второй параметр; в противном случае это stdout.Странное поведение функции с переменным числом параметров в C

Он отлично работает, если я указываю имя файла, проблема в том, что я не делаю (например, find("foo")). В этом случае он записывает результат в файл с именем foo вместо stdout.

В чем причина?

void find(char* word, ...) 
{ 
va_list list; 
char *fname = NULL; 
va_start(list, word); 
FILE* f; 
fname = strdup(va_arg(list, char*)); 
va_end(list); 
if (<condition>) // condition suited for the case in which the file name is received 
    f = fopen(fname, "a"); 
else 
    f = stdout; 
if (member(word)) 
    fprintf(f, "True\n"); 
else 
    fprintf(f, "False\n"); 
} 

На месте <condition> я попытался fname != NULL и strlen(fname) > 0, но те, не применяются, и он продолжает видеть fname в word когда fname не указано.

Большое спасибо за любую помощь, которую вы можете предоставить.

+1

varargs не предполагается использовать таким образом. Вам лучше использовать 'void find (char * word, char * filename)' и проверить, является ли 'filename'' NULL', и если так писать в stdout. Также не забудьте закрыть файл, который вы открыли, если вы открыли файл. –

ответ

6

От человека страница va_* «s:

Если нет следующего аргумента, или если тип не совместит с типом фактического следующего аргумента (поощряемым в соответствии с аргументом по умолчанию рекламные акции), случайные ошибки будут происходить.

Если вы хотите использовать список переменных параметров, необходимо разработать какой-то терминатор для списка (например, всегда добавить фиктивный аргумент NULL):

find (word, NULL); 
find (word, filename, NULL); 

или поставить число параметр как параметр:

find (1, word); 
find (2, word, filename); 
+0

OK, спасибо, что помните меня. Он работает с NULL в конце списка. Первоначально я думал, что NULL (или другое поведение) каким-то образом подразумевается для аргументов, которые не были получены, но он не знает сам по себе, когда список заканчивается. – thehousedude