If you enter integer value the loop works just fine but if you enter some ASCII character or float type value the program goes into an infinite loop. Any fix for this issue?
Technically, char is one type of int so this shouldn't be a problem.
#include <stdio.h>
int main(void)
{
int num;
scanf("%d",&num);
while (num < 40)
{
printf("Number is small\n");
scanf("%d",&num);
}
return 0;
}
The function scanf will try to read a decimal integer from stdin. It uses the definition of a decimal integer from strtol:
The valid integer value consists of the following parts:
(optional) plus or minus sign
(optional) prefix (0) indicating octal base (applies only when the base is 8 or 0)
(optional) prefix (0x or 0X) indicating hexadecimal base (applies only when the base is 16 or 0)
a sequence of digits
In other words, scanf will try to interpret a sequence of characters on stdin as a decimal integer. It will not do a character to integer conversion based on the ASCII table.
The solution to your problem lies in checking the return value of scanf, which is:
Number of receiving arguments successfully assigned (which may be zero in case a matching failure occurred before the first receiving argument was assigned), or EOF if input failure occurs before the first receiving argument was assigned.
So, check if scanf did not return 1. In this case, it has not read a decimal integer and num has not been assigned a value and should not be used.
In the given program, if num has never been assigned a value, its value is indeterminate. This could be a value <40, explaining the infinite loop as scanf repeatedly tries to read a non-integer from stdin, fails and leaves the non-integer on stdin as is. If num has been assigned a value before, it will still hold that value after a failed scanf call.
Related
so I need to create a program in C that reads a string character by character and output each character in the string's corresponding ascii decimal/hexadecimal/octal representation. This program should stop reading the string upon reaching a newline character.
For example given "Hi" the program should print "72 105" if I chose the decimal option.
So my idea is to read the string provided character by character into a large character array checking each character to see if it is the new line and then afterwards looping through elements 0-N where N is the index where char_array[N]=='\n' printing each element as its decimal representation.
So far, I've come up with this code which should cover the decimal representation case but I've come across an error I'm unsure how to troubleshoot.
#include <stdio.h>
int main(){
char char_arr[1000],conversion,temp;
int i=-1,j=0;
printf("Integer conversion in decimal (d), octal (o), or hexadecimal (h)? ");
scanf("%c",&conversion);
printf("Enter a message: ");
do{ i++;
if(scanf("%c",&char_arr[i])!=1){
break;}
}
while(char_arr[i]!='\n');
for(j=0;j<i;j++){
printf("%d",char_arr[j]);
}
return 0;
}
When I run this program it simply prints
Integer conversion in decimal (d), octal (o), or hexadecimal (h)? d
Enter a message:
and gives me no option to enter a message.
Does anyone have any thoughts or explanations for why this would occur? I'm new to C.
What is the output of this code if I input 25 to scanf()? I run this program, the output is 1 but I don't understand why? Can anyone explain?
#include <stdio.h>
#include <stdlib.h>
int main() {
int i;
printf("%d\n",scanf("%d",&i));
return 0;
}
scanf() returns the number of arguments successfully assigned. In your case, scanf only has one directive which has a respective argument to be assigned, so it returns 1 if the input conversion was done successfully.
1 is given now as argument to printf, which prints 1 into the output.
With the premise that the scanf() conversion was successfully,
printf("%d\n", scanf("%d",&i));
is basically equivalent to
printf("%d\n", 1);
Going straight forward
int i = 0, j = 0;
printf("%d\n", scanf("%d %d", &i, &j));
with the input of
25(enter)
50(enter)
and both conversions done successfully, would gave you the output 2 and
printf("%d\n", scanf("%d %d", &i, &j));
would basically be equivalent to
printf("%d\n", 2);
Side Note:
The return value of scanf() should always be checked by the algorithm but it is more an objective to the program to see if an input failure occurred than to diagnose it directly to the user.
These functions (scanf family) return the number of input items successfully matched and assigned.
So in this case it can return 1 if the scan was successful or 0 if not. If there is an error in the input stream it can also return EOF
Scanf is a basic function in C language.Since every function return a type of value or null,Scanf function returns numbers of inputs scanned successfully.
For Example: Scanf("%d%d") scans for 2 inputs, so it returns value 2.
Scanf("%f%d%d%d") scans for 4 inputs, so it returns value 4.
&variable_name is used to store the scanned value in the variable by using address-of operator.For scanning string, &-address-of operator can be neglible.
Example scanf("%s",variable)
Printf is a function which returns number of characters printed.It can be used with format specifer like %d,%f etc.
In the above program
printf("%d\n",scanf("%d",&i));
Scanf is first executed by scanning one integer input as %d is specified and stored in the variable of type int. Scanf returns value 1 since it is scanning only one input.
Printf function prints the value 1.Printing value does not depend upon input value.It depends only on number of inputs , scanf is scanned successfully.
you are outputting the scanf function which returns the variable numbers not the value in i.
I'm writing a program to rotate the letters of a string a certain direction through the alphabet. It takes an initial input of an integer, which I'll call N, then uses that integer as the number of letters that each character will be shifted through the alphabet. A positive integer shifts to the right of the alphabet, and a negative integer shifts to the left. For example, if the input was:
-2 cdefg
the output would be
abcde
In order to do this, I need to differ between regular alphabetic characters and integers in order to get the initial N. I've tried using scanf() with %d and the isalpha() function, as well as %c and the isdigit() function, but both seem to have obstacles for me. To clarify, I'm simply having trouble with the initial variable N. I don't know how to tell the difference between an input of 'm' between an integer. To my understanding, it would store the ASCII value of 'm' for N.
Read in a whole line of text and store it in an array. You can use fgets or – if you have it – getline for this.
Then you convert the first “word” on that line to a number using strtol. It tells you the position end at which it stopped parsing.
Advance the end pointer as long as it dereferences to white-space (you can check this via isspace).
Now you're at the position of the first character you need to rotate. Proceed until the end of the string.
you don't need to distinguish them. N is always before the string, so just read both, using the appropriate formats.
scanf("%d %s", &n, string);
To tell if the user entered correct input, check the value that scanf returns. It returns the number of items successfully converted. If the user doesn't type an integer first, the %d conversion will fail, so it will return 0. If the user types a valid integer before the string, it will return 2.
Why the output is '4' ? , while input is 'A'
int main() { int a = 5;
if(scanf("%d",&a))
printf("%d",a+1);
else
printf("%d",a-1);
}
When type sepcifier %d is used then the function expects that a valid signed decimal integer number will be entered. It is evident that symbol 'A' is not a number so the input failed.
Now a question arises: what will the function return in this case?
According to the description of function scanf (the C Standard, 7.21.6.4 The scanf function):
3 The scanf function returns the value of the macro EOF if an input
failure occurs before the first conversion (if any) has completed.
Otherwise, the scanf function returns the number of input items
assigned, which can be fewer than provided for, or even zero, in the
event of an early matching failure.
So the condition in the if statement
if(scanf("%d",&a))
evaluated to 0 (false) and the else statement was executed.
else
printf("%d",a-1);
that outputed 4.
Take into account that in general you may enter symbol 'A' for integers. But in this case the corresponding integer variable must be declared as unsignedand format specifier of scanf must to be %x
For example
#include <stdio.h>
int main( void )
{
unsigned int a = 5;
if ( scanf( "%x", &a ) )
{
printf( "%u\n", a + 1 );
}
else
{
printf( "%u\n", a - 1 );
}
}
In this case the output will be 11.:) scanf will consider symbol 'A' as a hexadecimal representation of 10.
You instructed scanf to read a signed integer. The input didn't even start with a sign or digit, so scanf didn't find a signed integers, so scanf returned 0 (the number of input items successfully matched and assigned), dropping you into the else clause of the if. Since scanf didn't match anything, it didn't assign anything, meaning a wasn't changed, and a-1 is 4.
You didn't specify what you were expecting, so I don't know what fix to suggest.
In scanf() All the arguments you pass are pointers. There's no default-promotion among pointers, and it is crucial that you pass the exact format specifier that matches the type of the pointer.
for more clearance:-
Click here!
This question already has answers here:
Why does scanf fail with floats?
(3 answers)
Closed 8 years ago.
So I was wondering what happens if the user enters characters in integer variables for example:
main()
{
int number;
printf("Print a number:");
scanf(" %d", &number);
printf("The result is:%d", number);
return 0;
}
I typed in characters and the result is: 1986895412
is this 1986895412 a place in the ram ??
In this case, scanf directive just fails. Quoting this answer (which essentially rephrases the spec's definition):
The %d conversion specifier expects the input text to be formatted as
a decimal integer. If it isn't, the conversion fails and the character
that caused the conversion to fail is left in the input stream.
So, number remains with the same value it had before the directive. As you didn't initialize it with some defined value (like int number = 0), it'll be just some random garbage value. In your case that happened to be equal to 1986895412.
Check the return of scanf(). When you type in characters, the correspond result will occur.
if (1 == scanf("%d", &number)) {
printf("The result is:%d", number);
}
else {
printf("Invalid data entered. `number` not changed\n");
}
Note: Code's int number; is not initialized, so its value could be any int. With invalid input, number was not changed and code printed the uninitialized number which just happeded to have the value of "1986895412". It may differ tomorrow.
Note: leading space in " %d" is not needed as %d itself consume leading whitespace.
As number had not been initialized and scanf() failed the printf() provokes undefined behaviour reading the uninitialised variable number. Anything could happen.
So there are two lessons to learn here:
Initialise variables when they are defined. (If you do not know to what to initialise them you most probably do not need them, at least not where you are trying to define them)
Perform error checking on calls which would return garbage if failed.