2013-08-27 2 views
1

Вот некоторые C код:Printf на Linux против Windows,

int i; 
printf("This text is printed\nThis text is not until the for loop end."); 
for (i = 5; i > 0; i--) 
{ 
    printf("%d", i); 
    sleep(1); 
} 

Почему остальная часть текста после '\n' не печатается перед начать цикл for? Даже printf внутри цикла for печатается только после конца цикла. Если я положил '\n' в конце текста, он печатает, но я не хочу новой строки.

Это происходит только в Linux, а не в Windows (только что сменил sleep (1) на Sleep (1000) и добавил windows.h).

+0

Ответ дан: http://stackoverflow.com/questions/1716296/why-does-printf-not-flush-after-the-call-unless-a-newline-is-in-the-format-strin – dcaswell

+0

Windows и Linux имеют очень разные драйверы вывода консоли. В Linux вывод буферизуется до тех пор, пока '\ n' не произойдет в случае вашей программы. – lurker

+0

Почему, по-вашему, вам не нужна новая строка в конце вашего вывода? Должна быть причина, по которой вы (и многие другие программисты Windows) не выводите ее, но, похоже, это странно для программистов Unix (например, я) - так же, как вывод, что вывод строки новой строки кажется странным для программистов Windows. В Unix вы делаете это, чтобы удостовериться, что выход произведен - так что для этого есть веская причина. В Windows, по-видимому, режим по умолчанию соответствует небуферизированному, поэтому все выходные данные генерируются по завершении вызова. –

ответ

3

Это вызвано буферизацией вывода. Когда вы вызываете printf, вывод не печатается немедленно. Он записывается в буфер для вывода в будущем. Обычно символ \n вызывает сброс буфера автоматически. Вы также можете очистить буфер вручную стандартный вывод:

printf("This text is printed\nThis text is not until the for loop end."); 
fflush(stdout); 
1

Посмотрите setvbuf() и _IONBF против _IOLBF против _IOFBF. По умолчанию, когда выход относится к терминалу, выход буферизируется по строке (_IOLBF). Это означает, что вывод появляется только при включении новой строки. _IONBF не забуферирован, иногда зарезервирован для стандартной ошибки (хотя это тоже может быть буферизировано в строке). _IOFBF полностью забуферирован; вывод не будет отображаться до тех пор, пока внутренний буфер не будет заполнен, или вы явно выберете вывод (или, иногда, если вы читаете со стандартного ввода). Если вы пишете в трубку или файл, выход обычно будет полностью буферизирован.

В общем, вы должны ожидать завершения выходов с помощью новой строки, если вы хотите своевременно их увидеть. (Это распространенный meme на Stack Overflow, который достаточно надежно идентифицирует, когда программа написана для Windows.)

1

Буфер stdout не указан стандартом C. Но POSIX подразумевает (не требует), что обычно stdout является строковым буфером, когда он подключен к терминалу, в противном случае полностью буферизуется.

Linux следует этому соглашению POSIX, но Windows этого не делает. Вы можете изменить поведение по умолчанию с помощью setvbuf или использовать fflush для очистки вывода, что гарантируется стандартом C.

Смежные вопросы