Thread: A weird question.

  1. #1
    Registered User
    Join Date
    Jun 2009
    Posts
    9

    Question A weird question.

    Okay, so I'm basically trying to get a single number from a single line text file... only I haven't gotten to that point because something weird is going on.

    The entire contents of the text file is this:

    Code:
    frame= 3900 fps=274 q=3.0 Lsize=   12043kB time=162.50 bitrate= 607.1kbits/s
    But when I run my program, the output is this:
    Code:
    frame= 3609 fps=275 q=3.0 size=   11034kB time=150.24 bitrate= 609.9kbits/s
    I'm sure I've done something really stupid here.... but what's going on? Why are the numbers changing?

    Code:
    #include <stdio.h>
    #include <stdlib.h>
    #include <limits.h>
    
    main()
    {
    	
    	char oneline[LINE_MAX];
    
    
    	FILE *logfile; 
    
    	logfile = fopen("out.txt", "r");
    
    	if (logfile == NULL)
    	{
    		printf("Couldn't open\n");
    		exit(1);
    	}
    
    	fgets(oneline, LINE_MAX, logfile);
    	fclose(logfile);
    	printf("%s\n", oneline);
    	
    	exit(0);
      
    }

  2. #2
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,412
    Could you be reading the wrong file? Are you sure that the contents of the file is what you think it is? (E.g., did you save the file?)
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  3. #3
    and the Hat of Guessing tabstop's Avatar
    Join Date
    Nov 2007
    Posts
    14,336
    Probably a difference between the file you're reading and the file you think you're reading.

  4. #4
    Frequently Quite Prolix dwks's Avatar
    Join Date
    Apr 2005
    Location
    Canada
    Posts
    8,057
    Make sure that you're running the program from the right directory. If you run "cat out.txt" in Linux or "type out.txt" in Windows from the command prompt in the same directory, it will show you the file your program is reading. If you didn't catch that, try looking at the file in notepad.
    dwk

    Seek and ye shall find. quaere et invenies.

    "Simplicity does not precede complexity, but follows it." -- Alan Perlis
    "Testing can only prove the presence of bugs, not their absence." -- Edsger Dijkstra
    "The only real mistake is the one from which we learn nothing." -- John Powell


    Other boards: DaniWeb, TPS
    Unofficial Wiki FAQ: cpwiki.sf.net

    My website: http://dwks.theprogrammingsite.com/
    Projects: codeform, xuni, atlantis, nort, etc.

  5. #5
    Registered User
    Join Date
    Jun 2009
    Posts
    9
    Arrrrgh! Nope, it's definitely the same file. I've checked, double checked, rechecked, deleted everything, tried again, and still the same results
    Then I tried copying and pasting from here and making the text file from scratch, and it works fine... which doesn't help me at all. So I guess there's some weird characters in my file or something.

    Here's the whole story: ffmpeg is called with execl, and the output is sent to a text file, as you can see here:

    Code:
    	pid_t my_pid, parent_pid, child_pid;
    	int fd; /*file descriptor to the file we will redirect ls's output*/
    
    		/* print error message if fork() fails */
    	if((child_pid = fork()) < 0 )
        {
    		perror("fork failure");
    		exit(1);
    	}
    	
    	if(child_pid == 0)
    	{
    		if((fd = open("output.log", O_RDWR | O_CREAT))==-1) /*open the file */
    		{
    			perror("opening the file");
    			return 1;
    		}
    	
    		dup2(fd,STDOUT_FILENO); /*copy the file descriptor fd into standard output*/
    		dup2(fd,STDERR_FILENO); /* same, for the standard error */
    		close(fd); /* close the file descriptor as we don't need it more  */
    
    		execl("/usr/bin/ffmpeg", "ffmpeg", "-i", infile_value, "-s", "320x240", "-r", "24", "-acodec", "libmp3lame", "-vcodec", "libxvid", "-vtag", "XVID", "-f", "avi", "-qscale", "3", "-g", "300", "-deinterlace", "-ab", "56k", "-ar", "24000", "-aspect", "4:3", "-async", "1", outfile_value, (char *) 0);
    		exit(1);
    	}
    	else
    	{
    		wait(NULL);
    	}
    I couldn't just do system("ffmpeg blah blah > output.txt); because I end up with a blank file.

    I'm just trying to get the length of the file, so I can use system() with grep now to grab the line with the number I need:

    Code:
    system("cat output.log|grep time= > out.txt");
    Which brings me to where I am now. I know I'm probably doing things in a weird way, but I don't know anyone personally who knows a thing about programming, so it's hard to ask how to go about doing things. Basically I need to get the duration of the video in seconds, so basically I just need to retrieve the "162.50" from the text file.

    If there's a better way to get the output of ffmpeg, or do anything I'm trying to do here, I'd love to know that as well.

  6. #6
    Frequently Quite Prolix dwks's Avatar
    Join Date
    Apr 2005
    Location
    Canada
    Posts
    8,057
    If you're on Linux (which I suspect you are ) you could use a command like this.
    Code:
    system("ffmpeg blah blah > output.txt 2>&1");
    The "2>&1" redirects standard error into standard output -- I'm assuming that ffmpeg prints this information to stderr, since you "end up with a blank file". (I don't have it installed to check.)
    dwk

    Seek and ye shall find. quaere et invenies.

    "Simplicity does not precede complexity, but follows it." -- Alan Perlis
    "Testing can only prove the presence of bugs, not their absence." -- Edsger Dijkstra
    "The only real mistake is the one from which we learn nothing." -- John Powell


    Other boards: DaniWeb, TPS
    Unofficial Wiki FAQ: cpwiki.sf.net

    My website: http://dwks.theprogrammingsite.com/
    Projects: codeform, xuni, atlantis, nort, etc.

  7. #7
    Registered User
    Join Date
    Jun 2009
    Posts
    9
    Aha, thanks, that did work... which eliminates the need for all the forking... though I'm glad I went through that and learned a bit.

    BUT it still doesn't solve my problem. The original code I posted there still outputs something completely different from "cat out.txt", and this is certainly nothing to do with me mixing up files.


    ARGH!!!

  8. #8
    Frequently Quite Prolix dwks's Avatar
    Join Date
    Apr 2005
    Location
    Canada
    Posts
    8,057
    Well, it looks to me like you're creating output.log but reading from out.txt. Do you execute that system() command in between?
    dwk

    Seek and ye shall find. quaere et invenies.

    "Simplicity does not precede complexity, but follows it." -- Alan Perlis
    "Testing can only prove the presence of bugs, not their absence." -- Edsger Dijkstra
    "The only real mistake is the one from which we learn nothing." -- John Powell


    Other boards: DaniWeb, TPS
    Unofficial Wiki FAQ: cpwiki.sf.net

    My website: http://dwks.theprogrammingsite.com/
    Projects: codeform, xuni, atlantis, nort, etc.

  9. #9
    and the Hat of Guessing tabstop's Avatar
    Join Date
    Nov 2007
    Posts
    14,336
    Now we're down to checking silly things:
    Is your .c file newer than your executable file (meaning you haven't compiled)?

  10. #10
    Frequently Quite Prolix dwks's Avatar
    Join Date
    Apr 2005
    Location
    Canada
    Posts
    8,057
    Also, by the way:
    Code:
    $ echo frame= 3900 fps=274 q=3.0 Lsize=   12043kB time=162.50 bitrate= 607.1kbits/s | perl -ne '/\w+=\s*\d+\s+\w+=\s*(\d+)/ && print $1,"\n"'
    274
    $
    Something to consider.

    I'm using Perl's regular expression matching. \w is a word character, \s is a space character; + means one or more, * means zero or more, and parentheses mean to save the expression into $1, which I then print.

    You could also strip spaces before and after the '=' and then use awk to print the second column. Anyway, I could pump out any number of shell commands to do this, but you probably aren't interested.
    dwk

    Seek and ye shall find. quaere et invenies.

    "Simplicity does not precede complexity, but follows it." -- Alan Perlis
    "Testing can only prove the presence of bugs, not their absence." -- Edsger Dijkstra
    "The only real mistake is the one from which we learn nothing." -- John Powell


    Other boards: DaniWeb, TPS
    Unofficial Wiki FAQ: cpwiki.sf.net

    My website: http://dwks.theprogrammingsite.com/
    Projects: codeform, xuni, atlantis, nort, etc.

  11. #11
    Registered User
    Join Date
    Jun 2009
    Posts
    9
    Okay, so I found some more out.

    When ffmpeg displays what's going on, it doesn't just scroll past with information. As it goes through the encoding process, it shows the data on the screen, in a static place, and the numbers increase as it progresses. Probably using ncurses or something.

    So I noticed a weird thing. You'd think that text file would be 77 bytes long. Nope, it's 2383 bytes long.

    While "cat out.txt" just displays one line of text, if I open it in emacs, I get this:


    frame= 143 fps= 0 q=3.0 size= 186kB time=5.83 bitrate= 261.5kbits/s ^Mframe= 259 fps=258 q=3.0 size= 492kB tim\
    e=10.68 bitrate= 377.1kbits/s ^Mframe= 376 fps=250 q=3.0 size= 858kB time=15.58 bitrate= 451.0kbits/s ^Mframe= 4\
    95 fps=247 q=3.0 size= 1348kB time=20.57 bitrate= 536.9kbits/s ^Mframe= 632 fps=252 q=3.0 size= 1702kB time=26.21 \
    bitrate= 532.1kbits/s ^Mframe= 777 fps=259 q=3.0 size= 2032kB time=32.26 bitrate= 516.2kbits/s ^Mframe= 914 fps=2\
    61 q=3.0 size= 2440kB time=37.97 bitrate= 526.5kbits/s ^Mframe= 1047 fps=261 q=3.0 size= 2894kB time=43.51 bitrate=\
    544.9kbits/s ^Mframe= 1190 fps=264 q=3.0 size= 3186kB time=49.44 bitrate= 527.9kbits/s ^Mframe= 1328 fps=265 q=3.0\
    size= 3586kB time=55.20 bitrate= 532.1kbits/s ^Mframe= 1469 fps=267 q=3.0 size= 4036kB time=61.10 bitrate= 541.1kb\
    its/s ^Mframe= 1600 fps=266 q=3.0 size= 4347kB time=66.55 bitrate= 535.1kbits/s ^Mframe= 1726 fps=265 q=3.0 size= \
    4767kB time=71.78 bitrate= 544.0kbits/s
    And so on, until we're at the final line.
    So I guess there's some strange character in there for every time it rewrote the text to the screen.

    Oh, and if I open it in gedit, then its all in a nice clean list like:

    frame= 143 fps= 0 q=3.0 size= 186kB time=5.83 bitrate= 261.5kbits/s

    frame= 259 fps=258 q=3.0 size= 492kB time=10.68 bitrate= 377.1kbits/s

    frame= 376 fps=250 q=3.0 size= 858kB time=15.58 bitrate= 451.0kbits/s

    frame= 495 fps=247 q=3.0 size= 1348kB time=20.57 bitrate= 536.9kbits/s
    etc...
    Anyone know how to get what I want out of there?
    Last edited by IanKoro; 06-05-2009 at 11:01 AM.

  12. #12
    and the Hat of Guessing tabstop's Avatar
    Join Date
    Nov 2007
    Posts
    14,336
    Quote Originally Posted by IanKoro View Post
    Anyone know how to get what I want out of there?
    Which one do you want?

    You could just read in a loop, continually overwriting the previous line buffer until you get to the last one.

  13. #13
    Frequently Quite Prolix dwks's Avatar
    Join Date
    Apr 2005
    Location
    Canada
    Posts
    8,057
    I'd guess ffmpeg prints \r, which puts the cursor back to the beginning of the line, so that it can repaint the line. As for what you want, sure! Perl coming up.
    Code:
    cat input | perl -ne '/.*fps=\s*(\d+)/ && print $1'
    The .* skips other characters, so that you get the last fps= part. That's pretty inefficient, but if that bothers you, you can read the string in with C or C++ and search backwards for the string "fps", skip '=' and skip spaces, and then use sscanf() in C or istringstream in C++ to get the number itself.

    [edit]
    You could just read in a loop, continually overwriting the previous line buffer until you get to the last one.
    Notice that that won't quite work -- it's all one line. I don't think fgets would stop at a \r, but then again, maybe it would. Or you could code it to. [/edit]
    dwk

    Seek and ye shall find. quaere et invenies.

    "Simplicity does not precede complexity, but follows it." -- Alan Perlis
    "Testing can only prove the presence of bugs, not their absence." -- Edsger Dijkstra
    "The only real mistake is the one from which we learn nothing." -- John Powell


    Other boards: DaniWeb, TPS
    Unofficial Wiki FAQ: cpwiki.sf.net

    My website: http://dwks.theprogrammingsite.com/
    Projects: codeform, xuni, atlantis, nort, etc.

  14. #14
    Registered User
    Join Date
    Jun 2009
    Posts
    9
    Hrmm, okay, that will likely do what I need... (I actually need the 'time' part, not the 'fps', but obviously that can be adapted easily.)

    I have a job interview shortly.... so I'd better go and get ready for that, if I sit here tinkering around any more I'll never get out the door on time, so I'll see if I can make that work this evening.

    These forums are great.. I'm getting excited about programming all over again! I can't wait to jump back into some of the games and things I abandoned in frustration without having anyone to ask about the problems I'd run into.
    Thank you very much!

  15. #15
    Registered User
    Join Date
    Oct 2008
    Location
    TX
    Posts
    2,059
    See if there are invisible / control characters embedded in your input file by filtering it through cat, as in
    Code:
    cat -vet input_file

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. another do while question
    By kbpsu in forum C++ Programming
    Replies: 3
    Last Post: 03-23-2009, 12:14 PM
  2. Kind of a weird question
    By Lurker in forum A Brief History of Cprogramming.com
    Replies: 13
    Last Post: 10-23-2003, 01:37 AM
  3. Question...
    By TechWins in forum A Brief History of Cprogramming.com
    Replies: 16
    Last Post: 07-28-2003, 09:47 PM
  4. opengl DC question
    By SAMSAM in forum Game Programming
    Replies: 6
    Last Post: 02-26-2003, 09:22 PM
  5. Weird Question maybe
    By Unregistered in forum C++ Programming
    Replies: 3
    Last Post: 12-27-2001, 07:30 PM