Home > Software engineering >  why %*c not working in the expression "%[^\n]s%*c"
why %*c not working in the expression "%[^\n]s%*c"

Time:04-13

Here is the code :

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

struct driverDetail
{
    char name[20];
    int licenseNumber;
    char route[20];
    int kms;
};

int main()
{
    struct driverDetail drivers[1];

    for (int i = 0; i < 1; i  )
    {
        printf("\nEnter details for driver %d :\n", i 1);
        printf("Enter driver's name : ");
        scanf("%[^\n]s%*c", &drivers[i].name);
        printf("Enter driver's license number : ");
        scanf("%[^\n]d%*c", &drivers[i].licenseNumber);
        printf("Enter driver's route : ");
        scanf("%[^\n]s%*c", &drivers[i].route);
        printf("Enter driver's kilometers driven : ");
        scanf("%[^\n]d%*c", &drivers[i].kms);
    }

    for (int i = 0; i < 1; i  )
    {
        printf("driver %d name : %s\n", i 1, drivers[i].name);
        printf("driver %d license number : %d\n", i 1, drivers[i].licenseNumber);
        printf("driver %d route : %s\n", i 1, drivers[i].route);
        printf("driver %d kilometers driven : %d\n", i 1, drivers[i].kms);
    }

    return 0;
}

%[^\n]%*c works completely fine but why %[^\n]s%*c is not working.

when I use %[^\n]%*c \n gets rejected by the first format specifier and then %*c read the \n and discards it. But why *%c is not discarding \n when used with %[^\n]s%*c.

Same case with %d, *%c works with %d%*c but not with %[^\n]d%*c.

Why is this happening ? can somebody explain.

CodePudding user response:

When scanf reads input according to one of the formats %[^\n]s%*c and %[^\n]d%*c, and the behavior is well defined (i.e. the object receiving the data corresponding to the %[ directive is not overrun), there must be either an input failure or a matching failure at the s or d. This is because scanf will expect each of these to match a literal character (a literal 's' or 'd'), but if there are any more characters available then the next one must be a newline. Anything else will have been consumed by the %[.

Perhaps you meant %[^\n]%d, %[^\n]%*s, or similar. The %s and %d directives skip leading whitespace, including newlines (unlike %c or %*c), so they would attempt to read past the newline (if any) up next in the input.

Note also that all of these alternatives afford the possibility of an input failure, as I already mentioned. That is, if the %[ consumes all the bytes up to the end of the stream, such that there are none left to read, then scanf quits. Its return value will reflect that. Take care, however, not to confuse "end of stream" with the temporary absence of characters to read. These are not at all the same thing.

  • Related