#include <stdio.h>
#include <time.h>
#include <stdlib.h>
void delay(double sec)
{
clock_t start = clock();
while ((clock() - start) / CLOCKS_PER_SEC < sec)
;
}
int main()
{
for (int i = 0; i < 100000; i++) {
printf("%d ", i);
delay(1);
}
return 0;
}
I wrote a delay function and tested it with this code, but I didn't see any number in standard output.
Then I changed the printf() call like this :
printf("%d \n", i);
Interestingly, it worked. I also tried without delay function like this:
for (int i = 0; i < 100000; i++)
printf("%d ", i);
It also worked. What am I missing here? Why can't I see any number when I run the first code? Thanks for helps :)
Because the output is buffered. Most terminals will buffer the standard-output until either a newline (\n) is encountered, or fflush(stdout) is called.
Your loop that includes the call to delay should eventually print the numbers, but when the program is finished.
Add fflush(stdout); after the printf-call to make the numbers appear immediately without newlines in between.
Well, there are two reasons. First, printf() doesn't always flush its output, so you may actually get past the printf statement and still not see anything on your terminal. The text is buffered. Putting in a \n may have caused it to flush its output, so that's why that worked.
The second problem is that you are not passing any value to your delay() function. So it's probably using some random value, and hanging.
I'd also like to point out that clock() returns CPU time, not "wall clock" time, so it may actually take longer than you think.
Delay functions are tricky, that's why there are lots of system calls to do them. See sleep().
Related
#include <stdio.h>
#include <wiringPi.h>
#include <softPwm.h>
int main(void)
{
wiringPiSetupGpio();
for(int i = 0 ; i <50; i++)
{
if ( i%10 == 1)
{
printf("\n");
}
printf("%d ", i);
delay(1000);
}
return 0;
}
I'm working in rasberry pi environment.
I want to print a number for each 1 second. But this code did not print a number one by one but
print 10 numbers for each 10 seconds. This code gives 10 numbers in line at once. What's the problem??
The stdout channel is line buffered by default. This means that data sent to stdout won't necessarily appear until a newline character is printed.
If you call fflush(stdout), any buffered output will be immediately printed.
printf("%d ", i);
fflush(stdout);
in order to print the values at the running time using printf you need to add \n so try this may work.
#include <stdio.h>
#include <wiringPi.h>
#include <softPwm.h>
int main(void)
{
wiringPiSetupGpio();
for(int i = 0 ; i <50; i++)
{
if ( i%10 == 1)
{
printf("\n");
}
// a `\n` added at the end of the string!
printf("%d \n", i);
delay(1000);
}
return 0;
}
for more info read this question's answer
The problem is probably that the output stream is not being flushed. I suggest that you call fflush( stdout ); before the delay(1000); function call. This will ensure that all printed data actually becomes observable, before the program enters a wait state.
Normally, it is not necessary to explicitly flush an output stream, because the output will become visible sooner or later. For example, the output buffer will usually get implicitly flushed whenever you read input or when the program ends. Also, if your program is writing output to the user's screen (in contrast to, for example, writing output to a file), then the output stream is probably line-buffered, which means that the output stream will get implicitly flushed whenever a newline character is written.
However, in this case, it appears that the implicit flushing mentioned above is not sufficient. Therefore, you will have to revert to explicit flushing using the function fflush, as mentioned above.
I'm struggling to make a timer in c that counts minutes and seconds. I'm trying to test it by printing the time to the console but it doesn't seem to show anything. Does anything look wrong in my code?
#include <stdio.h>
#include <stdlib.h>
#include <windows.h>
#define TRUE 1
int main( void )
{
int min = 0;
int sec = 0;
while (TRUE)
{
sec++;
Sleep(1000);
printf("%2d:%2d", min, sec);
if (sec == 59)
{
min++;
sec = 0;
}
}
return 0;
}
For performance reason, printf is buffered. That is, it won't display until the buffer is full. First thing to try is to add a new-line character to the end:
printf("%2d:%2d\n", min, sec);
If that doesn't work, you can force the output buffer to flush by calling fflush(stdout);
I would just check the system time rather than keeping track of seconds/minutes. This is because, your Sleep may not be exactly 1000ms, so over time your counter will not be accurate.
Since you're using Windows, here's a slightly modified version of your code:
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <windows.h>
int main()
{
for (;;)
{
time_t now = time(NULL);
struct tm* ptm = localtime(&now);
printf("%02d:%02d\n", ptm->tm_min, ptm->tm_sec);
Sleep(1000);
}
return 0;
}
I hope that helps.
As you ask, there are several things wrong in your code, I'll tell you as I read it. See below.
#include <stdio.h>
#include <stdlib.h>
#include <windows.h>
#define TRUE 1
int main( void )
{
int min = 0;
int sec = 0;
while (TRUE)
{
sec++;
Sleep(1000);
There's a problem with Sleep(). The thing is that you ask the kernel to pause your program for 1000 milliseconds, but that means that the kernel will awake your program 1 second after your call it to pause. This doesn't take into account the fact that the kernel will put in the schedule queue your process and it will, in general never take the cpu immediately, but after some delay. Then, even if you get the cpu immediately, your code will need some time to execute, making the total loop longer than 1000 ms. And your clock will be slow. It is better to get the system time and show it on the screen, or to take a timestamp when you start... and then show the difference in time from the start time to the timestamp you get at each display. The system time is maintained by an interrupt, that happens at regular intervals (by means of a precise clock oscillator) so you'll get a good clock time that way, instead of your slow clock (how slow it is will depend on things like how many other processes you are running on the system)
printf("%2d:%2d", min, sec);
This has already been stated in other answers, but let me explain how it works so you can understand how buffering works. A buffer is a large block of memory (normally it is 512 bytes) that is filled by printf() so it only calls write() when it has filled a complete buffer of data. This allows stdio to save system calls to do the actual writing and so, be more efficient when transferring large amounts of data.
On interactive applications, this is not applicable, as no output would be done if you don't force the buffers to fflush() before any input is done, so when the output is a tty device (something that stdio can know from the file descriptor associated to standard output) then it switches to line mode buffering, and that means that printf() will flush out the buffer when: 1) it is filled up, or 2) when a newline \n character is found in the output. So, one way to solve your problem is to put a \n at the end of the string, or to call fflush(stdout); after calling printf().
if (sec == 59)
as you increment your seconds before comparing, you have to check against 60 and not 59, as you compare with 60 to convert it to 0 after you have already incremented the seconds.
{
min++;
You should have to do the same with the minutes, when minutes get to 60. As you have not included this code, I assume you are not considering an hours chrono.
sec = 0;
}
}
return 0;
}
A complete solution for what I mean can be:
#include <stdlib.h>
#include <stdio.h>
#include <time.h>
#include <windows.h>
int main()
{
long start_timestamp;
long display_timestamp;
start_timestamp = time(NULL);
for(;;) { /* this is the same as while(TRUE) */
display_timestamp = time(NULL);
int elapsed = display_timestamp - start_timestamp;
int min = elapsed / 60;
int sec = elapsed % 60;
/* the \r in next printf will make to print a single carry
* return in the same line, so the time updates on top of
* itself */
printf("\r%02d:%02d", min, sec); fflush(stdout);
Sleep(100); /* as you print the time elapsed, you don't
* mind if you shorten the time between
* displays. */
}
}
Does anything look wrong in my code?
Several things look wrong. The first is stdout line buffering - see eduffy's answer for that.
The second problem is that you're doing sec++; sleep(1000);, which means that sec will be incremented once every 1000 seconds or more.
The third problem is that if(sec == 59; is wrong and needs to be if(sec == 60). Otherwise you'll have 59 seconds per minute.
The fourth problem is that sleep(1) will sleep for at least 1 second, but may sleep for 2 seconds, or 10 seconds, or 1234 seconds. To guard against this you want something more like this:
expiry = now() + delay;
while(true) {
sleep(expiry - now() ):
expiry += delay;
}
The basic idea being that if one sleep takes too long then the next sleep will sleep less; and it'll end up being "correct on average".
The last problem is that sleep() doesn't really have enough precision. For 1 second delays you want to be able to sleep for fractions of a second (e.g. like maybe 9/10ths of a second). Depending on which compiler for which OS, there's probably something better you can use (e.g. maybe nanosleep()). Sadly there may be nothing that's actually good (e.g. some sort of "nanosleep_until(expiry_time)" that prevents jitter caused by IRQs and/or task switches that occur after you determine now but before you call something like "nanosleep()").
I have a program that should produce output on stdout, and transient status information on stderr. Programs with similar results might include rsync or apt (though their output is sufficiently complex that reducing it to the essentials I need is daunting).
This program seems like it should work as described, but does not:
#include <stdio.h>
#include <limits.h>
void *work () {
for (long i = 0; i < LONG_MAX; i++) {
if (i % 100000000 == 0) {
fprintf(stdout, "%ld\n", i);
}
fprintf(stderr, "\rrunning %ld", i);
}
return 0;
}
int main() {
work(0);
fprintf(stderr, "\ndone\n");
return 0;
}
The status info is updated in place via stderr as desired, but only a single line of output appears via stdout. If the stderr status fprintf is removed, then all stdout output appears as expected.
What is going on here?
This code is correct (well, the void * return from work() is bad form--void would be far better).
I suspect that the problem is simply that you are not waiting long enough--it takes time to iterate through 100,000,000 iterations, especially with output each time through the loop (remember--you will be blocking on output once you fill the stdout buffer).
I estimate it will take a minimum of 3 minutes before you get the second output to stdout.
I am new to C programming.
I am trying to work through an example in my textbook.
Problem:
1 : Can't make random number generator pause for one second, without having to
insert printf(); in a place where I shouldn't.
2: Can't make the program pause for 1 second, and then delete random sequence. I have tried using printf(\r), but it just deletes the entire sequence without pausing for 1 second.
Help appreciated.
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
int main(void)
{
time_t Start_Of_Seq = (time(NULL));
time_t Now = 0;
Now = clock();
srand((unsigned int)Start_Of_Seq);
for(int i = 1; i <= 5; i++)
{
printf("%d",rand()% 10);
}
printf("\n"); //This shouldn't be here.
for(; clock() - Now < CLOCKS_PER_SEC;);
printf("Testing the to see if there is a pause\n");
}
The printf function outputs everything to a buffer. The buffer is actually printed only after a newline. Try fflush(stdout); to print the buffer contents immediately.
Besides, if you use Linux or another Unix-like system, for pauses there is a system call sleep. Try the man 3 sleep command to see more info.
So my problem is my program runs too fast that I can't see how it behaves. It's supposed to make the text crawl along the edges of the terminal. I tried to use sleep() to make a short pause betweenprintf(...)s so that it I can see where the text us going while it prints.
This is what it looks like:
http://i.imgur.com/B6FFbNp.gif
So I put sleep() function after the printfs so that it will pause before starting the loop again and make the text move slowly. But what happens is it pauses the programs indefinitely before it even starts. This also happens with usleep and system("pause 1"). This is what it looks like:
http://i.imgur.com/krGW3lB.gif
==================================================================================
EDIT:
Okay, I figured it out on my own. It seems that sleep() only works if I put \n in my strings. I don't know why. I didn't even read this in the damn manuals.
So if you have
printf("HELLO\n");
sleep(3);
printf("HELLO\n");
sleep(3);
printf("HELLO\n");
It will result in:
HELLO
[pause for 3 seconds]
HELLO
[pause for 3 seconds]
HELLO
but if you remove the newline characters it will:
[pause for 9 seconds]
HELLO HELLO HELLO
I don't know why this happens but it just does
==================================================================================
EDIT:
This is how I wanted my program to work:
http://i.imgur.com/DXv7E60.gif
Thank you for your answers
Your observations do not due to sleep() not working, but to the fact that printf() uses stdout, which is line buffered. "line buffered" means, that what has been written to stdoutis buffered until the end of the line is reached before the buffer's content it is flushed out.
So after the first printf("HELLO"); the output does not go to the screen but stays in the buffer, then sleep(1); is executed and makes you wait. Then for the next printf("HELLO"); the output still does not go to the screen, but the following sleep(1); again makes you wait for 1 second ... and so on until a line end if reached by your program printing a '\n' or by the program's end, which implicitly flushes the output buffer to the console.
You can avoid the behaviour by flushing stdout's output buffer explicitly after every printf():
#include <stdio.h>
#include <unistd.h>
int main(void)
{
printf("HELLO");
fflush(stdout);
sleep(3);
printf("HELLO");
fflush(stdout);
sleep(3);
printf("HELLO");
/* fflush(stdout); */ /* not needed as buffers are implicitly flushed on the program's end */
return 0;
}
A quick hack I usually do is make some buffer array (eg. char buf[10]) and place an fgets() in between iterations, which forces the program to wait for a newline from the user. So, for example, if we had:
.
.
.
for(i = 0; i < 1000000; ++i)
printf("%d\n", i);
we could then do
.
.
.
char buf[10];
for(i = 0; i < 1000000; ++i){
printf("%d\n", i);
fgets(buf, 10, stdin);
}
and control the iterations with the enter key.
We could also stop every nth iteration by using a modulus. Using the above example, we will now stop every 100 iterations:
.
.
.
char buf[10];
for(i = 0; i < 1000000; ++i){
printf("%d\n", i);
if(i % 100 == 0)
fgets(buf, 10, stdin);
}
A more time consuming but effecient way is to use a dedicated debugger like GDB.