Basically what my program does is take multiple lines of input from the user and displays a chart when the user quits the program. The issue i'm running into is that there are different variations for how the user can input information, for example: "L 200000" or "J 3.5 12". I'm not having an issue so much as to what the input itself is just how scanf() interprets it. I know that if I did scanf("%s" "%i", &identifier, &number) it would work just fine for the first example but as soon as the user inputs three separate values that single scanf() no longer works. So my question is, how would I get scanf() to ignore the fact there are missing values but still be able to assign what it's given to pre-defined variables? Is there any other methods that would work besides scanf()?
Asked
Active
Viewed 102 times
0
-
9Don't use `scanf` for this. It's just not well suited for such a task. Use alternatives such as `fgets` to read the whole line and then `strtok` to parse each token. Or read the first character which presumably describes the data format that follows and then maybe `scanf` at that point. But would still advise against `scanf` as it can be difficult to get right in any non-trivial use cases. – kaylum Sep 07 '21 at 21:42
-
1See [What can I use for input conversion instead of scanf?](https://stackoverflow.com/questions/58403537) – Steve Summit Sep 07 '21 at 22:24
-
Input the line with `fgets` and apply `sscanf` calls first to convert supposed 3 inputs and second to convert 2 inputs if that fails. How do you know it fails? By testing how many conversions were successful (its function return value), which is *essential* when using any of the `scanf` function family. – Weather Vane Sep 07 '21 at 22:29
-
Please clarify your specific problem or provide additional details to highlight exactly what you need. As it's currently written, it's hard to tell exactly what you're asking. – Community Sep 13 '21 at 22:06
1 Answers
3
Is there any other methods that would work besides scanf()?
Stop using scanf()
. It does not well handle ill-formatted data, leaving stdin
is a challenging state for alternative processing.
Use fgets()
to read a line of user input into a string – then process the string.
#define EXPECTED_LINE_LENGTH_MAX 100
char buf[EXPECTED_LINE_LENGTH_MAX*2 + 1]; // Be generous
if (fgets(buf, sizeof buf, stdin)) {
Now parse buf
for various formats.
Using " %n"
to store the offset of the scanning is very useful to detect trailing junk.
int n = 0;
int identifier;
double number
if (sscanf(buf, "L %d %n", &identifier, &n) == 1 && buf[n] == '\0') {
puts("Found L data");
} else if (sscanf(buf, "J %lf %d %n", &number, &identifier, &n) == 2 && buf[n] == '\0') {
puts("Found J data");
} else {
puts("Fail");
}
}

chux - Reinstate Monica
- 143,097
- 13
- 135
- 256