0

I am currently learning how to write to txt file in c. I encountered a problem where the first column of text won't output the string it has been given.

#include <stdio.h>
#include <string.h>

int main() {
    FILE * fptr;

    //open file
    fptr = fopen("test.txt", "a");

    //entering how many lines will be used
    int columns;
    scanf("%d", &columns);

    //loop for writing in lines
    for (int i = 0; i < columns; i++) {
        char temp_text[10001];
        fgets (temp_text, 10000, stdin);

        //to remove the \n caused by fgets
        temp_text[strlen(temp_text) - 1] = '\0';

        //fprintf is compatible with placeholders
        fprintf (fptr, "data %d: %s\n", i, temp_text);

    }

    //closing file
    fclose (fptr);

    return 0;
}

The inputs are:

5
qw 
er
ty
ui

I expected it to ask for n (in this case 5) time/s, instead it always asks for one less. The txt file shows:

data 0: 
data 1: qw
data 2: er
data 3: ty
data 4: ui

A shown, it always skips putting the given string on the first line as well.

Thank you in advance.

  • Don't mix `scanf()` with `fgets()`. (Use the latter.) Scanf has left a dangling LF in the input buffer... Your output is exactly what `fgets()` has loaded, beginning with a LF and nothing else. You could skip the '5' and just let `fgets()` read to the end of the file... – Fe2O3 Dec 13 '22 at 05:34
  • @picchiolu It is, but I find the answers to the one I've linked are more on point regarding the question at hand. – moooeeeep Dec 13 '22 at 08:01
  • Actually, the answers to both are not too good. I'd like to refer to a good fgets/sscanf-based answer. Did you notice one? – moooeeeep Dec 13 '22 at 08:05
  • @moooeeeep oh yes, no criticism implied in my comment. I was trying to show that the same issue had already surfaced a few times. – picchiolu Dec 13 '22 at 08:05
  • 1
    Maybe this would be a relevant link too: https://stackoverflow.com/q/22330969/1025391 – moooeeeep Dec 13 '22 at 08:08

1 Answers1

0

In the code posted by the OP, immediately after the user enters the value for columns, the program enters the for loop and tries to read from stdin, which happens to be just a LF (line-feed). For the OP's code to work, the user would have to enter, say, 5 blabla instead of just 5, when requested for the number of columns, so that fgets has something to read after scanf has consumed the digits for columns.

As the problem is related to the way the code handles user's input, I altered the original code so that it doesn't open/write to a file and uses scanf instead of fgets in the loop, and I tested it on https://www.programiz.com/c-programming/online-compiler/. The following version works as expected:

#include <stdio.h>
#include <string.h>

int main() {
    //FILE * fptr;

    //open file
    //fptr = fopen("test.txt", "a");

    //entering how many lines will be used
    int columns;
    printf("Enter n of cols: ");
    scanf("%d", &columns);

    //loop for writing in lines
    for (int i = 0; i < columns; i++) {
        char temp_text[100];
        scanf ("%s", &temp_text);

        //to remove the \n caused by fgets
        //temp_text[strlen(temp_text) - 1] = '\0';

        //fprintf is compatible with placeholders
        printf ("entered for %d: %s\n", i, temp_text);

    }

    //closing file
    //fclose (fptr);

    return 0;
}
picchiolu
  • 1,120
  • 5
  • 20