Quote Originally Posted by Nominal Animal View Post
The buffer in the example program contains each line read. You can use the line variable to point at the start of the line.


You can use sscanf() to "read" (or convert) the line you've already read. That man page is very detailed, but unfortunately it's a bit confusing to read at first.

For example, try and see what happens if you rewrite the loop in the example program into
Code:
    while (1) {
        char value[400];
        int key;

        line = fgets(buffer, sizeof buffer, fp);
        if (!line)
            break;

        /* Convert the line read into a key, and a value. */
        if (sscanf(line, " %d %399s", &key, value) != 2) {
            /* Remove the newline at the end of the line. */
            line[strcspn(line, "\r\n")] = '\0';

            /* Output an error and abort. */
            fprintf(stderr, "'%s': Bad data line, '%s'.\n", filename, line);
            return EXIT_FAILURE;
        }

        printf("Key = %d, value = '%s'\n", key, value);
    }
A couple of important points you should understand:
  • The %d conversion converts an int.
    The function takes a pointer to an int as a parameter, here &key, where the result will be stored.
  • The %s conversion copies a string that does not contain whitespace (spaces, tabs, newlines).
    The function takes a pointer to a char as a parameter, here value (because it is a char array, it gets converted to a pointer to the first char in the array automatically, just as if you had written &(value[0])), where the string will be copied to. There must be enough room to store the token, and an extra end-of-string mark (NUL byte, \0).
  • Since we only have room for 400 characters including the end-of-string mark in value, value can contain at most a 399-character string. We must limit the conversion so we won't overrun the buffer.
    Fortunately this is very simple: we just include the maximum length before the conversion specifier. So, we actually need to use %399s.

Since tokens end at whitespace, values cannot contain spaces or tabs.

If you want the value to extend to the end of the line, you can use
Code:
        if (sscanf(line, " %d %399[^\r\n]", &key, &value) != 2) {
The %[...] conversion is like the %s conversion, except only characters specified in ... are accepted. You can use ranges; for example 0-9A-Za-z accepts all numbers and letters. If the first character is ^, the meaning is inverted: ^\r\n accepts all characters except CR (\r) or LF (\n).
Thanks so much.
You're the best guy ever.
You're best than my teachers, you explain everything so detailed!