Taking some string input from user with C - c

I am not too familiar with C syntax. I need to process some data based on user input. Although I processed the data successfully but I am stuck at user input section. I removed the unnecessary data processing section and made a simple example of how I am taking the user input. Can anyone tell me what's the problem with below code :
int i, number;
char *str;
str=(char*)malloc(1000*sizeof(char));
printf("Enter count : ");
scanf("%d", &number);
for(i=0; i<number; i++)
{
printf("\nEnter string: ");
scanf ("%[^\n]%*c", str);
printf("%s", str);
}
Output:
"Enter count : " appears fine, but whenever I provide some value and hit enter it's showing me only 'count' number of Enter string: without enabling user to enter the string.
For example -
Enter count : 2
Enter string:
Enter string:
But if I discard the count input section and provide any fixed value, like
for(i=0; i<5; i++)
it works fine
Thanks in advance

FYI, there is no issue in for(i=0; i<number; i++), problem is in scanning logic.
Actually, scanf ("%[^\n]%*c", str); is not right. you should use %s to read strings, not %c, which reads a single character, including the ENTER (newline).
Rather, i would suggest, use fgets() for inputs. It's a whole lot better in every way. Check the man page here.
Maybe you can use something like
//Dummy code
int i, number;
char *str;
printf("Enter count : ");
scanf("%d", &number);
str=malloc(number*sizeof(char)); //yes, casting not required
fgets(str, (number-1), stdin ); //"number" is used in different context
fputs(str, stdout);
EDIT:
Working code
#include <stdio.h>
#include <stdlib.h>
#define SIZ 1024
int main()
{
int i, number;
char * str = malloc(SIZ * sizeof (char));
printf("Enter the number :\n");
scanf("%d", &number);
getc(stdin); //to eat up the `\n` stored in stdin buffer
for (i = 0; i < number; i++)
{
printf("Enter the string %d :", (i+1));
fgets(str, SIZ-1, stdin);
printf("You have entered :");
fputs(str, stdout);
}
return 0;
}

scanf("%s",str); Use this instead of the code you are using to take string inputs in a character array.

There is a newline character \n after entering count value which is picked up by %c in your scanf()
Just use %s to scan strings as shown below.
scanf("%s",str);
If there are spaces in your input.
Then do
char c[50];
fgets(c,sizeof(c),stdin);
Check the below code:
#include <stdio.h>
#include<stdlib.h>
int main(){
int i, number;
char *str;
str=malloc(1000*sizeof(char));
printf("Enter count : ");
scanf("%d%*c", &number);
for(i=0; i<number; i++)
{
printf("\nEnter string: ");
fgets(str,1000,stdin);
printf("%s", str);
}
}

Related

Why does the number 10 get output in each iteration and how can I fix this?

I have a for loop, which I want to get the input from the user and print the associated ascii value. But it only asks for the user input in the second iteration, which is followed and preceded by the output 10. I tried to get rid of new-line characters, but it still prints out 10.
#include <stdio.h>
int main(void){
int number;
printf("Enter the number:");
scanf("%i", &number);
for( ; number > 0; number--){
char character;
printf("Give a char: \n");
scanf("%c", &character);
printf("The associated ascii value is %i \n", character);
}
return 0;
}
Maybe simpler (though using scanf() for user input is not recommended)
scanf(" %c", &character);
// ^ skip otional leading whitespace
Your whole program using fgets() for user input (and my indentation, spacing, style; sorry)
#include <stdio.h> // printf(), fgets()
#include <stdlib.h> // strtol()
int main(void) {
int number;
char buffer[100]; // space enough
printf("Enter the number:");
fgets(buffer, sizeof buffer, stdin);
number = strtol(buffer, 0, 10); // error checking missing
for (; number > 0; number--) {
printf("Give a char: ");
fgets(buffer, sizeof buffer, stdin); // reuse buffer, error checking missing
if (buffer[0] != '\n') {
printf("The associated ascii value of '%c' is %i.\n", *buffer, *buffer);
}
}
return 0;
}
This should solve your problem. getchar() will read the extra newline character from buffer.
#include <stdio.h>
int main(void){
int number;
printf("Enter the number:");
scanf("%i", &number);
for( ; number > 0; number--){
char character;
printf("Give a char: ");
getchar();
scanf("%c", &character);
printf("The associated ascii value is %i \n", character);
}
return 0;
}
regarding;
scanf("%c", &character);
the first time through the loop the '\n' is input.
on all following passes through the loop, the scanf() fails, so the value in character does not change.
This is a prime example of why your code should be error checking.
for instance, to error check the call to scanf():
if( scanf("%c", &character) != 1 )
{
fprintf( stderr, "scanf for a character failed\n" );
break;
}
the 1 is because the scanf() family of functions returns the number of successful: input format conversion specifiers or EOF and it is best to assure the 'positive' status.

Taking a string input using gets() function in C [duplicate]

I'm pretty new to C, and I have a problem with inputing data to the program.
My code:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(void) {
int a;
char b[20];
printf("Input your ID: ");
scanf("%d", &a);
printf("Input your name: ");
gets(b);
printf("---------");
printf("Name: %s", b);
system("pause");
return 0;
}
It allows to input ID, but it just skips the rest of the input. If I change the order like this:
printf("Input your name: ");
gets(b);
printf("Input your ID: ");
scanf("%d", &a);
It will work. Although, I CANNOT change order and I need it just as-is. Can someone help me ? Maybe I need to use some other functions. Thanks!
Try:
scanf("%d\n", &a);
gets only reads the '\n' that scanf leaves in. Also, you should use fgets not gets: http://www.cplusplus.com/reference/clibrary/cstdio/fgets/ to avoid possible buffer overflows.
Edit:
if the above doesn't work, try:
...
scanf("%d", &a);
getc(stdin);
...
scanf doesn't consume the newline and is thus a natural enemy of fgets. Don't put them together without a good hack. Both of these options will work:
// Option 1 - eat the newline
scanf("%d", &a);
getchar(); // reads the newline character
// Option 2 - use fgets, then scan what was read
char tmp[50];
fgets(tmp, 50, stdin);
sscanf(tmp, "%d", &a);
// note that you might have read too many characters at this point and
// must interprete them, too
scanf will not consume \n so it will be taken by the gets which follows the scanf. flush the input stream after scanf like this.
#include <stdlib.h>
#include <string.h>
int main(void) {
int a;
char b[20];
printf("Input your ID: ");
scanf("%d", &a);
fflush(stdin);
printf("Input your name: ");
gets(b);
printf("---------");
printf("Name: %s", b);
system("pause");
return 0;
}
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(void) {
int a;
char b[20];
printf("Input your ID: ");
scanf("%d", &a);
getchar();
printf("Input your name: ");
gets(b);
printf("---------");
printf("Name: %s", b);
return 0;
}
Note:
If you use the scanf first and the fgets second, it will give problem only. It will not read the second character for the gets function.
If you press enter, after give the input for scanf, that enter character will be consider as a input f or fgets.
you should do this way.
fgetc(stdin);
scanf("%c",&c);
if(c!='y')
{
break;
}
fgetc(stdin);
to read input from scanf after reading through gets.
scanf("%d", &a); can't read the return, because %d accepts only decimal integer. So you add a \n at the beginning of the next scanf to ignore the last \n inside the buffer.
Then, scanf("\n%s", b); now can reads the string without problem, but scanf stops to read when find a white space. So, change the %s to %[^\n]. It means: "read everthing but \n"
scanf("\n%[^\n]", b);
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(void) {
int a;
char b[20];
printf("Input your ID: ");
scanf("%d", &a);
printf("Input your name: ");
scanf("\n%[^\n]", b);
//first \n says to ignore last 'return'
//%[^\n] read until find a 'return'
printf("---------\n");
printf("Name: %s\n\n", b);
system("pause");
return 0;
}
The scanf function removes whitespace automatically before trying to parse things other than characters. %c, %n, %[] are exceptions that do not remove leading whitespace.gets is reading the newline left by previous scanf. Catch the newline usinggetchar();
scanf("%d", &a);
getchar(); // catches the newline character omitted by scanf("%d")
gets(b);
https://wpollock.com/CPlus/PrintfRef.htm
Just use 2 gets() functions
When you want to use gets() after a scanf(), you make sure that you use 2 of the gets() functions and for the above case write your code like:
int main(void) {
int a;
char b[20];
printf("Input your ID: ");
scanf("%d", &a);
//the change is here*********************
printf("Input your name: ");
gets(b);
gets(b);
//the change is here*********************
printf("---------");
printf("Name: %s", b);
system("pause");
return 0;
}

Output printed twice instead of once [duplicate]

I tried to execute the following simple code in ubuntu 15.10 But the code behaves odd than expected
#include<stdio.h>
int main(){
int n,i=0;
char val;
char a[20];
printf("\nEnter the value : ");
scanf("%s",a);
printf("\nEnter the value to be searched : ");
scanf("%c",&val);
int count=0;
for(i=0;i<20;i++){
if(a[i]==val){
printf("\n%c found at location %d",val,i);
count++;
}
}
printf("\nTotal occurance of %c is %d",val,count);
return 0;
}
output:
--------------------------
Enter the value : 12345678
Enter the value to be searched :
Total occurance of is 0
The second scanf to get the value to be searched seems not to be working. The rest of the code executes after the first scanf without getting input second time.
After first scanf(), in every scanf(), in formatting part, put a whitespace
So change this
scanf("%c",&val);
into this
scanf(" %c",&val);
Reason is, scanf() returns when it sees a newline, and when first scanf() runs, you type input and hit enter. scanf() consumes your input but not remaining newline, so, following scanf() consumes this remaining newline.
Putting a whitespace in formatting part makes that remaining newline consumed.
You can use fgets():
#include<stdio.h>
int main() {
int n, i = 0;
char val;
char a[20];
printf("\nEnter the value : ");
fgets(a, 20, stdin);
printf("\nEnter the value to be searched : ");
scanf("%c", &val);
int count = 0;
for (i = 0; i < 20; i++) {
if (a[i] == val) {
printf("\n%c found at location %d", val, i);
count++;
}
}
printf("\nTotal occurance of %c is %d", val, count);
return 0;
}
or clear stdin:
#include<stdio.h>
void clearstdin(void) {
int c;
while ((c = fgetc(stdin)) != EOF && c != '\n');
}
int main() {
int n, i = 0;
char val;
char a[20];
printf("\nEnter the value : ");
scanf("%s",a);
clearstdin();
printf("\nEnter the value to be searched : ");
scanf("%c", &val);
int count = 0;
for (i = 0; i < 20; i++) {
if (a[i] == val) {
printf("\n%c found at location %d", val, i);
count++;
}
}
printf("\nTotal occurance of %c is %d", val, count);
return 0;
}
Also, see C: Multiple scanf's, when I enter in a value for one scanf it skips the second scanf
printf("\nEnter the value : ");
scanf("%s",a);
printf("\nEnter the value to be searched : ");
scanf("%d",&val); // here is different
i don't know why, but code above working...
scanf("%d",&val);
You can use " %c" instead of "%c" for the format string. The blank causes scanf() to skip white space (including newlines) before reading the character.

How to read string followed by character in c?

#include<stdio.h>
int main() {
char *str, ch;
int count = 0, i;
printf("\nEnter a string : ");
scanf("%s", str);
printf("\nEnter the character to be searched : ");
scanf("%c", &ch);
for (i = 0; str[i] != '\0'; i++) {
if (str[i] == ch)
count++;
}
if (count == 0)
printf("\nCharacter '%c'is not present", ch);
else
printf("\nOccurence of character '%c' : %d", ch, count);
return (0);
}
while i executing this code the string is taken after that it will not taking any characters and showing results.
Your code might crash (happened to me when verifying it on my machine) because you did not allocate space for str...
you should change char *str, ch; to something like char *str = malloc(100), ch;
Also, change scanf("%c", &ch); to scanf(" %c", &ch); to resolve your problem. This happens because when you enter your string, you end it with enter, and that enter is consumed by your next scanf(%c) and so, your second scanf() only reads the enter instead of reading the char you intend. scanf(" %c", &ch); will ignore all whitespaces, including the previously entered enter :-) and wil allow your char to be processed
Always write scanf like this, to read the previous newline character:
printf("\nEnter the character to be searched : ");
scanf(" %c", &ch);
OR
use getchar()
printf("\nEnter the character to be searched : ");
getchar();
scanf("%c", &ch);
Defining a max length would be the simplest way to solve this. Insted of using scanf, I would recomend using fgets as done below. It is much more failsafe since you can define the max number of characters to be read.
Tutorialspoint's explanation of fgets
#define MAX_LENGTH 100
int main() {
char str[MAX_LENGTH], ch;
int count = 0;
printf("\nEnter a string : ");
fgets(str, MAX_LENGTH, stdin);
printf("\nEnter the character to be searched : ");
scanf("%c", &ch);
...
}

fgets not waiting for user input

In the given code fgets is not waiting for input.
I tried using scanf but it's giving unusual error(Exception thrown at 0x0F74DDF4 (ucrtbased.dll)). I'm using Visual Studio 2015 for debugging my code. Can anyone explain why fgets is not waiting for input?
#include<stdio.h>
#include<stdlib.h>
#include<process.h>
//GLOBAL-VARIABLE DECLARTION
#define MAX 1000
//GLOBAL-STRUCTURES DECLARATION
struct census
{
char city[MAX];
long int p;
float l;
};
//GLOBAL-STRUCTURE-VARIABLE DECLARATION
struct census cen[] = { 0,0,0 };
//USER-DEFINED FUNCTION
void header();
void header()
{
printf("*-*-*-*-*CENSUS_INFO*-*-*-*-*");
printf("\n\n");
}
//PROGRAM STARTS HERE
main()
{
//VARIABLE-DECLARATION
int i = 0, j = 0;
//int no_of_records = 0;
//FUNCTION CALL-OUT
header();
printf("Enter No. of City : ");
scanf_s("%d", &j);
printf("\n\n");
printf("Enter Name of City, Population and Literacy level");
printf("\n\n");
for (i = 0;i < j;i++)
{
printf("City No. %d - Info :", i + 1);
printf("\n\n");
printf("City Name :");
fgets(cen[i].city, MAX, stdin);
printf("\n");
printf("Population : ");
scanf_s("%d", &cen[i].p);
printf("\n");
printf("Literacy : ");
scanf_s("%f", &cen[i].l);
printf("\n");
}
//TERMINAL-PAUSE
system("pause");
}
When you enter the number of cities and press Enter, scanf doesn't read the linebreak character from input. fgets then tries to read but finds the linebreak, and immediately stops.
Don't use scanf to read numbers, use fgets to read in string first and then sscanf(or strtol/strtof/strtod) to convert to number.
char temp[LIMIT];
if(fgets(temp, LIMIT, stdin)) {
if(sscanf(temp, "%d", &j) == 1) {
// Ok
}
else {
// Handle sscanf error
}
}
else {
// Handle fgets error
}
I always use fgets followed by sscanf.
Declare this at the top,
char line[MAX];
Then use fgets to get a line, and sscanf to parse the int value out of it,
printf("Enter No. of City : ");
fgets(line, sizeof(line), stdin);
sscanf(line, "%d", &j);
Similar pattern for l
printf("Literacy : ");
fgets(line, sizeof(line), stdin);
sscanf(line, "%f", &cen[i].l);

Resources