scanf("%s %d %d", &value1[0], &value2, &value3)
The problem is scanf() can´t ignore the third conversion specifier. It still keeps trying to catch the decimal input for the third argument, value3.
To catching the whole input as string first and then later split the content of this string into each own object may be a better alternative.
fgets() is a litte more safer than scanf() when taking user input so I´ll use fgets().
char* fgets ( char * str, int num, FILE * stream );
With fgets() you need to define the amount of characters to read (num), which is a great feature for maintaining security, but in this case we don´t know what a user potentially will input as integer for the decimal input requests. If we specify to less characters for the digits, the rest digits will be left in stdin.
A workaround would be to specify the total amount of digits possible for representing integers of type int in decimal notation in the call to fgets().
These would be 10 digits for the total number of "2,147,483,647" on 64-bit architectures or 5 digits for the total number of "32,767" on 32-bit architectures. I go with the 64-bit case for now.
So 10 (value1) + 10 (value2) + 10 (value3) + 2space characters between value1 and value2 and between value2 and value3 + the terminating \0 for a string = 33 characters. Note that fgets() also reads the entered newline \n (but we later discard that from the string easily) so we need even one character more; it is in total 34 characters:
char buffer[34];
fgets(buffer,sizeof(buffer),stdin);
After that we need to proof how many content we have in the string stored in buffer. We can proof it implicitly by counting the space characters:
unsigned int mark;
for(unsigned int i = 0; i < (sizeof(buffer)/sizeof(buffer[0]) - 1)); i++)
{
if(buffer[i] == ' ')
mark++;
}
Thereafter we need to transfer/convert the individual content pieces inside the string in buffer to the appropriate own objects by using sscanf(). If we now have 2 space characters in the string, we can use 3 conversion specifiers in a sscanf command, else we have appropriate sscanf()s:
if(mark == 2)
{
sscanf(buffer,"%s %d %d", value1, &value2, &value3);
}
else if(mark == 1)
{
sscanf(buffer,"%s %d", value1, &value2);
}
else if(mark == 0)
{
sscanf(buffer,"%s", value1);
}
else
{
printf("The input entered is not valid!\n");
printf("Please try again!\n");
}
The whole code is then:
#include <stdio.h>
#include <string.h>
int main()
{
char value1[10];
int value2;
int value3;
unsigned int mark;
char buffer[34];
for(;;)
{
fgets(buffer,sizeof(buffer),stdin);
buffer[strcspn(buffer, "\n")] = 0;
mark = 0;
for(unsigned int i = 0; i < ((sizeof(buffer)/sizeof(buffer[0]) - 1)); i++)
{
if(buffer[i] == ' ')
mark++;
}
if(mark == 2)
{
sscanf(buffer,"%s %d %d", value1, &value2, &value3);
break;
}
else if(mark == 1)
{
sscanf(buffer,"%s %d", value1, &value2);
break;
}
else if(mark == 0)
{
sscanf(buffer,"%s", value1);
break;
}
else
{
printf("The input entered is not valid!\n");
printf("Please try again!\n");
}
}
printf("value1 = %s\n", value1);
if(mark == 1 || mark == 2)
printf("value2 = %d\n", value2);
if(mark == 2)
printf("value3 = %d\n", value3);
return 0;
}