Program is terminating without recognizing scanf - c

I don't know why my program terminates before confirmStats(); is called. I included everything related in main() in case the issue is ocurring somewhere else in my program.
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int str, intel, charis;
int totalPts =5;
/* Returns a number.
User must input an integer.
*/
int getNumber(int number){
while(scanf("%d", &number) != 1){
printf("You did not enter a valid number\n");
scanf("%*s");
}
return number;
}
/* Individual stat points */
int stat(int number){
number = getNumber(number);
while(number > totalPts){
printf("You only have %d stat points left\n", totalPts);
printf("Enter a number less than or equal to %d:\t", totalPts);
number = getNumber(number);
}
totalPts -= number;
printf("Points remaining:\t%d\n", totalPts);
return number;
}
/* Player stat points */
void getStats(){
printf("You're alotted %d stat points to spend in Strength, Intellect, and Charisma\n", totalPts);
printf("Intellect:\t");
intel = stat(intel);
printf("Strength:\t");
str = stat(str);
printf("Charisma:\t");
charis = stat(charis);
printf("\nIntellect: %d\t Strength: %d\t Charisma: %d\n", intel, str, charis);
}
void confirmStats(){
char ans;
scanf("%c", &ans);
while(ans == 'n'){
str = 0;
intel = 0;
charis = 0;
getStats();
printf("Are these correct?:\ty/n: ");
scanf("%c", &ans);
}
}
void main(){
printf("\nSafe choice...");
printf("\n");
printf("Alright, how old are you?\n");
// int age, str, intel, charis;
int age;
// int totalPts = 5;
age = getNumber(age);
getStats();
printf("Are these correct? ");
printf("\n");
printf("y/n:\t");
printf("\n");
confirmStats();
}

The problem is that scanf("%c", &ans); scans the newline character left over by the previous scanf.
The fix is easy. Simply add a space before %c in the two scanfs in confirmStats. The space is a whitespace character and a whitespace character in the format string of scanf tells scanf to scan any number of whitespace characters, if any, until the first non-whitespace character.
Improved code:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int str, intel, charis;
int totalPts = 5;
/*
Returns a number.
User must input an integer.
*/
int getNumber(){
int number;
while(scanf("%d", &number) != 1){
printf("You did not enter a valid number\n");
scanf("%*s");
}
return number;
}
/* Individual stat points */
int stat(){
int number;
number = getNumber();
while(number > totalPts){
printf("You only have %d stat points left\n", totalPts);
printf("Enter a number less than or equal to %d:\t", totalPts);
number = getNumber();
}
totalPts -= number;
printf("Points remaining:\t%d\n", totalPts);
return number;
}
/* Player stat points */
void getStats(){
printf("You're alotted %d stat points to spend in Strength, Intellect, and Charisma\n", totalPts);
printf("Intellect:\t");
intel = stat();
printf("Strength:\t");
str = stat();
printf("Charisma:\t");
charis = stat();
printf("\nIntellect: %d\t Strength: %d\t Charisma: %d\n", intel, str, charis);
}
void confirmStats(){
char ans;
scanf(" %c", &ans);
while(ans == 'n'){
str = 0;
intel = 0;
charis = 0;
getStats();
printf("Are these correct?:\ty/n: ");
scanf(" %c", &ans);
}
}
int main(void){
printf("\nSafe choice...");
printf("\n");
printf("Alright, how old are you?\n");
age = getNumber();
getStats();
printf("Are these correct? ");
printf("\n");
printf("y/n:\t");
printf("\n");
confirmStats();
return 0;
}

int getNumber(int number){
int ok = 0;
while (!ok){
if(scanf("%d", &number) != 1){
printf("You did not enter a valid number\n");
while(getchar()!='\n');
}
else {
getchar();
ok=1;
}
}
return number;
}

Sir ,do u have checked the syntax is scant("%d",&variable);
Not. scant("%d",variable);

Related

Program (in C) doesn't start function, and it just simply ends

After running the next code, in the function get_data(), everything runs normally until I get to the end of the For, when program should call the function continue_function() but in somehow, ignores it, and the program just ends.
Am I calling it in a wrong way?
I'm just start learning programming in C and this is one of the last exam's exercises.
#include <stdio.h>
#define MAX 100
#define YES 1
#define NO 0
struct record
{
char fname[15+1];
char lname[20+1];
char phone[9+1];
long income;
int month;
int day;
int year;
};
struct record list[MAX];
int last_entry = 0;
void get_data(void);
void display_report(void);
int continue_function(void);
void clear_kb(void);
main()
{
int cont = YES;
int ch;
while(cont == YES)
{
printf("\n");
printf("\n MENU");
printf("\n =========\n");
printf("\n1. Enter Names");
printf("\n2. Print Report");
printf("\n3. Quit");
printf("\n\nEnter Selection ==> ");
scanf("%d", &ch);
clear_kb();
system("cls");
switch(ch)
{
case 1: get_data();
break;
case 2: display_report();
break;
case 3: printf("\n\nThank You for using this Program!");
cont = NO;
break;
default: printf("\n\nInvalid Choice, Please Select 1 to 3!");
break;
}
}
}
void get_data(void)
{
int cont;
int ctr;
for(cont = YES; last_entry < MAX && cont == YES; last_entry++)
{
printf("\n\nEnter information for Person %d.", last_entry+1);
printf("\n\nEnter first name: ");
gets(list[last_entry].fname);
printf("Enter last name: ");
gets(list[last_entry].lname);
printf("Enter phone in 123-4567 format: ");
gets(list[last_entry].phone);
printf("Enter Yearly Income: ");
scanf("%ld", &list[last_entry].income);
printf("Enter Birthday: ");
do
{
printf("\n\tMonth (0 - 12): ");
scanf("%d", &list[last_entry].month);
}
while (list[last_entry].month < 0 || list[last_entry].month > 12);
do
{
printf("\tDay (0 - 31): ");
scanf("%d", &list[last_entry].day);
}
while (list[last_entry].day < 0 || list[last_entry].day > 31);
do
{
printf("\tYear (1800 - 2025): ");
scanf("%d", list[last_entry].year);
}
while (list[last_entry].year < 1800 || list[last_entry].year > 2025);
cont = continue_function();
}
if(last_entry == MAX)
{
printf("\n\nMaximum Number of Names has been entered!\n");
}
}
void display_report(void)
{
long month_total = 0, grand_total = 0;
int x, y;
fprintf(stdout, "\n\n");
fprintf(stdout, "\n REPORT");
fprintf(stdout, "\n ========");
for(x = 0; x <= 12; x++)
{
month_total = 0;
for(y = 0; y < last_entry; y++)
{
if(list[y].month == x)
{
fprintf(stdout, "\n\t%s %s %s %ld", list[y].fname, list[y].lname, list[y].phone, list[y].income);
month_total += list[y].income;
}
}
fprintf(stdout, "\nTotal for month %d is %ld:", x, month_total);
grand_total += month_total;
}
fprintf(stdout, "\n\nReport Totals:");
fprintf(stdout, "\nTotal Income is %ld", grand_total);
fprintf(stdout, "\nAverage Income is %ld", grand_total/last_entry);
fprintf(stdout, "\n\n* * * End of Report * * *");
}
int continue_function(void)
{
char ch;
printf("\n\nDo you wish to continue? (Y)es/(N)o: ");
getc(ch);
while(ch != 'n' && ch != 'N' && ch != 'y' && ch != 'Y')
{
printf("\n%c is invalid!", ch);
printf("\n\nPlease enter \'N\' to Quit or \'Y\' to Continue: ");
getc(ch);
}
clear_kb();
if(ch == 'n' || ch == 'N')
{
system("cls");
return(NO);
}
else
{
system("cls");
return(YES);
}
}
void clear_kb(void)
{
char junk[80];
gets(junk);
}
You're not using your get functions properly:
https://www.tutorialspoint.com/c_standard_library/c_function_getc.htm
int getc(FILE *); for instance requires a FILE* as argument and returns the character, but you are passing the character as argument, it should look like ch = getc(stdin);.
On another note, notice that when you use scanf you pass &c? This is because for a value to be modified, you need to pass the address where it's stored (&) and not the value itself. So even if getc took a char, it would have to be getc(&ch).
You should follow a quick tutorial on pointers and types, if you come from a higher level language or if you're new that could be a good idea.

Scanf doesnt take more than 4 characters in a const char array - C

I have a really weird bug. If I write a name which contains more than 4 characters, the printf will only output the first 4 characters.
Important note: I am not allowed to use any other library than stdio.h and I am not allowed to use anything else than scanf for input and printf for output. Moreover I am not allowed to modify the paramater list of the functions and I have to use const char. The code runs on putty via ssh on a unix system.
My code and the input/output are below. In addition, the while loop has a bug too ._.
#include <stdio.h>
int searchCharacters(const char*, char);
int getLength(const char*);
int main() {
char yesNo;
int end = 0;
const char name[] = {""};
printf("please enter a name: ");
scanf("%s", name);
int length = getLength(name);
printf("\n%s has a length of %i", name, length);
fflush(stdin);
while(end != 1) {
printf("\n\nWould you like to search a character in %s (y / n)?", name);
scanf(" %c", &yesNo);
switch(yesNo) {
case 'y':
printf("\nPlease enter a character: ");
char searchingCharacter;
scanf("%c", &searchingCharacter);
int numberOfCharacters = searchCharacter(name, searchingCharacter);
printf("\nThe letter %c is %i-times", searchingCharacter, numberOfCharacters);
break;
case 'n':
printf("\nGood bye!");
end++;
break;
}
}
return 0;
}
int searchCharacter(const char s[], char c) {
int numberOfIterations = getLength(s);
int numberOfCharacters = 0;
int i;
for (int i = 0; i < numberOfIterations; i++) {
if (s[i] == c) {
numberOfCharacters++;
}
}
return numberOfCharacters;
}
int getLength(const char s[]) {
int i = 0;
while(s[i++]);
return (i - 1);
}
Input/Output:
please enter a name: abcdefg
abcd has a length of 7 characters.
Would you like to search a character in abcd (y / n)? y
<-------------- AUTOMATIC/BUG WHILE LOOP --------------------------->
Please enter a character:
The letter
is 0-times.
</--------------AUTOMATIC/BUG WHILE LOOP---------------------------->
Would you like to search a character in abcd (y / n)? n
Good bye!
So, here is a possible answer:
"Change const char name[] to char name[100]" (from #kaylum)
"Change scanf("%c", &searchingCharacter) --> scanf(" %c", %searchingCharacters) to consume new line in input stream" (from #user3121023)
Here is the full code:
#include <stdio.h>
int searchCharacters(const char*, char);
int getLength(const char*);
int main() {
char yesNo;
int end = 0;
char name[100]; <-- Changed -->
printf("please enter a name: ");
scanf("%99s", name);
fflush(stdin);
int length = getLength(name);
printf("\n%s has a length of %i", name, length);
while(end != 1) {
printf("\n\nWould you like to search a character in %s (y / n)?", name);
scanf("%c", &yesNo); <-- Changed -->
switch(yesNo) {
case 'y':
printf("\nPlease enter a character: ");
char searchingCharacter;
scanf(" %c", &searchingCharacter); <-- Changed -->
int numberOfCharacters = searchCharacter(name, searchingCharacter);
printf("\nThe letter %c is %i-times", searchingCharacter,
numberOfCharacters);
break;
case 'n':
printf("\nGood bye!");
end++;
break;
}
}
return 0;
}
int searchCharacter(const char s[], char c) {
int numberOfIterations = getLength(s);
int numberOfCharacters = 0;
int i;
for (int i = 0; i < numberOfIterations; i++) {
if (s[i] == c) {
numberOfCharacters++;
}
}
return numberOfCharacters;
}
int getLength(const char s[]) {
int i = 0;
while(s[i++]);
return (i - 1);
}
Input/Output:
please enter a name: abcdefg
abcdefg has a length of 7 characters. <-- Working/Changed -->
Would you like to search a character in abcd (y / n)? y
Please enter a character: a <-- Working/Changed -->
The letter a is 1-times. <-- Working/Changed -->
Would you like to search a character in abcdefg (y / n)? n
Good bye!

Properly buffering and validating string

I am getting a bit of an error in my program, it is somewhat basic but here is my error: I am trying to properly input a series of strings into a structure and it seems like user input is ending at the wrong spot.
#include <stdio.h>
#include <string.h>
#define buffer 256
struct Fisher
{
char SSN[8]; //9 digit max
char First_Name[12];
char Last_Name[15];
char Phone[10];
char Email[35];
}typedef Fisher;
void getFisher(Fisher* pfisher, int i);
void dispFisher(Fisher* pfisher, int i);
void Fisherman_Menu(Fisher* pfisher, int i);
int main()
{
int i = 0;
Fisher fisherarray[3];
Fisher* pfisher = &fisherarray[0];
Fisherman_Menu(pfisher, i);
return 0;
}
void Fisherman_Menu(Fisher* pfisher, int i)
{
for(;;)
{
fflush(stdin);
printf("-1-Register Fisherman\n");
printf("-2-Search Fisherman\n");
printf("-3-Go back to Main Menu\n");
fflush(stdin);
int choice=0;
scanf(" %d", &choice);
if (choice == 1)
{
fflush(stdin);
getFisher(pfisher, i);
i++;
}
if (choice == 2)
{
fflush(stdin);
dispFisher(pfisher, i);
}
else if (choice == 3)
{
break; /* Break out of loop */
}
else
printf("Anything else?\n");
}
/* When this function returns, you get back to the main menu */
}
void getFisher(Fisher* pfisher, int i)
{
char input[buffer];
char* pinput = NULL;
//===============================
printf("Enter Social Security Number: ");
pinput = fgets(input, buffer, stdin);//validate
strcpy((pfisher+i)->SSN, pinput);
//(pfisher+i)->SSN = atoi(pinput);
//==============================
printf("Enter first name: ");
pinput = fgets(input, buffer, stdin);//validates name
strcpy((pfisher+i)->First_Name, pinput);
//==============================
printf("Enter last name: ");
pinput = fgets(input, buffer, stdin);//validates name
strcpy((pfisher+i)->Last_Name, pinput);
//==============================
printf("Enter phone number as a 10 digit number (without any
dashes or spaces): ");
pinput = fgets(input, buffer, stdin);//validate phone
strcpy((pfisher+i)->Phone, pinput);
//(pfisher+i)->Phone = atoi(pinput);
//===============================
printf("Enter email address: ");
pinput = fgets(input, 20, stdin);//validates name
strcpy((pfisher+i)->Email, pinput);
}
void dispFisher(Fisher* pfisher, int i)
{
int len;
int pen;
printf("ssn is equal to: %s\n", ((pfisher+0)->SSN));
printf("First Name is equal to: %s\n", ((pfisher+0)->First_Name));
printf("ssn is equal to: %s\n", ((pfisher+1)->SSN));
printf("First Name is equal to: %s\n", ((pfisher+1)->First_Name));
len = strlen(((pfisher+0)->SSN));
printf("string length = %d\n", len);
pen = strlen(((pfisher+1)->SSN));
printf("string length = %d\n", len);
/*
int arr = 0;
char searchSSN[9];
printf("Enter SSN: ");
scanf("%s", &searchSSN);
for(arr = 0; arr < i; arr++)
{
if(strcmp(&searchSSN, (pfisher+arr)->SSN) == 0)
{
//printf("I is equal to: %s\n", (pfisher+i)->SSN);
printf("Fisher\n");
printf("-------------------------------------------\n");
printf("%d \n %s \n %s \n %s \n %s ", (pfisher + arr)->SSN, ((pfisher+arr)->First_Name), ((pfisher+arr)->Last_Name), ((pfisher+arr)->Phone), (pfisher+arr)->Email);
printf("-------------------------------------------\n");
}
}
*/
}
My output for SSN is getting messed up and becoming "123456789(FirstName string)
example: 123456789TurboTurkey
How can I clean up the length of the string and get in the SSN properly
There is no enough space to store 9 digit in SSN. If you want to store 9 digit in it, its size should be 10 (9 digit + NULL). If there is no NULL charactor, it will read near by locations too..

Why this function is giving unexpected result?

I was trying to co
So, I don't understand the reason why my compiler is not letting me take input when the convhex() is called from the main. It's directly printing some result.. I don't understand this.
Here's the code..
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <String.h>
void convhex();
void convert(int no, int base);
int checkValid(int base,int no);
// function prototyping done here
void convhex()
{
char ch[10];
int dec=0;
int i, res;
printf("Enter the hexadecimal number \n");
scanf("%[^\n]", ch);
// print in decimal
for(i=strlen(ch)-1;i>=0;i--)
{
if(ch[i]>65)
res=ch[i]-65+10;
else
res=ch[i]-48;
//printf("%d", res);
dec=dec+pow(16,strlen(ch)-(i+1))*res;
}
printf("\nThe number in decimal is %d \n", dec);
}
int checkValid(int base,int no)
{
int rem;
//flag;
// flag=0;
while(no>0)
{
rem=no%10;
if(rem>base)
{
//flag=1;
//break;
return 0;
}
no/=10;
}
return 1;
/*
if(flag==1)
printf("Invalid Input");
else
printf("Valid Input");
*/
}
void convert(int no, int base)
{
int temp, mod, sum=0, i=0;
temp=no;
while(temp>0)
{
mod=temp%10;
temp=temp/10;
sum=sum+pow(base,i)*mod;
i++;
}
printf("\n The number in base 10 is %d", sum);
}
int main()
{
int base, no;
printf("Enter the base \n");
scanf("%d", &base);
if(base==16)
convhex();
else
{
printf("Enter the number \n");
scanf("%d", &no);
printf("You have entered %d", no);
if(checkValid(base, no))
convert(no, base);
}
return 0;
}
// up until now our program can work with any base from 0-10 but not hexadecimal
// in case of hex, we have A-F
scanf in convhex is reading the \n left by the scanf in main.
Try this
scanf(" %[^\n]", ch);
^ An extra space will eat any number of white-spaces.
you can just remove the %[^\n] from scanf in connhex to change it to:
scanf("%s", ch)
or you could do what haccks suggested in the above post.

How to use a loop function with user input in C?

Here is the average program I created.
#include <stdio.h>
#include <stdlib.h>
int main()
{
float f1,f2,f3;
/* Program to calculate averages. */
/*Asks for the numbers.*/
printf(" Please enter three numbers.\n");
printf ("\t" "First number please.\n");
scanf("%f", &f1);
printf ("\t" "Second number please.\n");
scanf ("%f", &f2);
printf("\t" "Third number please.\n");
scanf("%f", &f3);
/* Now it averages it.*/
printf(" Thank you, wait one.\n");
printf(" Excellent, your sum is.\n");
printf("%f""\n", f1+f2+f3);
printf("Your average of the sum is now!!!!\n");
printf("%f", (f1+f2+f3)/3);
return 0;
}
Now would I turn this into a do-while? Or an if else?
If you want to repeat the whole entry and averaging process, you can wrap a loop around the code:
#include <stdio.h>
int main(void)
{
float f1,f2,f3;
while (1)
{
printf("Please enter three numbers.\n");
printf("\tFirst number please.\n");
if (scanf("%f", &f1) != 1)
break;
printf("\tSecond number please.\n");
if (scanf("%f", &f2) != 1)
break;
printf("\tThird number please.\n");
if (scanf("%f", &f3) != 1)
break;
printf("Your sum is %f\n", f1+f2+f3);
printf("Your average is %f\n", (f1+f2+f3)/3);
}
return 0;
}
Note that this code checks the return value from scanf() each time it is used, breaking the loop if there's a problem. There's no need for string concatenation, and a single printf() can certainly print a string and a value.
That's a simple first stage; there are more elaborate techniques that could be used. For example, you could create a function to prompt for and read the number:
#include <stdio.h>
static int prompt_and_read(const char *prompt, float *value)
{
printf("%s", prompt);
if (scanf("%f", value) != 1)
return -1;
return 0;
}
int main(void)
{
float f1,f2,f3;
while (printf("Please enter three numbers.\n") > 0 &&
prompt_and_read("\tFirst number please.\n", &f1) == 0 &&
prompt_and_read("\tSecond number please.\n", &f2) == 0 &&
prompt_and_read("\tThird number please.\n", &f3) == 0)
{
printf("Your sum is %f\n", f1+f2+f3);
printf("Your average is %f\n", (f1+f2+f3)/3);
}
return 0;
}
If you want to get away from a fixed set of three values, then you can iterate until you encounter EOF or an error:
#include <stdio.h>
static int prompt_and_read(const char *prompt, float *value)
{
printf("%s", prompt);
if (scanf("%f", value) != 1)
return -1;
return 0;
}
int main(void)
{
float value;
float sum = 0.0;
int num = 0;
printf("Please enter numbers.\n");
while (prompt_and_read("\tNext number please.\n", &value) == 0)
{
sum += value;
num++;
}
if (num > 0)
{
printf("You entered %d numbers\n", num);
printf("Your sum is %f\n", sum);
printf("Your average is %f\n", sum / num);
}
return 0;
}
You might also decide to replace the newline at the ends of the prompt strings with a space so that the value is typed on the same line as the prompt.
If you want to check whether to repeat the calculation, you can use a minor variant on the first or second versions of the code:
#include <stdio.h>
static int prompt_and_read(const char *prompt, float *value)
{
printf("%s", prompt);
if (scanf("%f", value) != 1)
return -1;
return 0;
}
static int prompt_continue(const char *prompt)
{
printf("%s", prompt);
char answer[2];
if (scanf("%1s", answer) != 1)
return 0;
if (answer[0] == 'y' || answer[0] == 'Y')
{
int c;
while ((c = getchar()) != EOF && c != '\n') // Gobble to newline
;
return 1;
}
return 0;
}
int main(void)
{
float f1,f2,f3;
while (printf("Please enter three numbers.\n") > 0 &&
prompt_and_read("\tFirst number please.\n", &f1) == 0 &&
prompt_and_read("\tSecond number please.\n", &f2) == 0 &&
prompt_and_read("\tThird number please.\n", &f3) == 0)
{
printf("Your sum is %f\n", f1+f2+f3);
printf("Your average is %f\n", (f1+f2+f3)/3);
if (prompt_continue("Do you want to try again?") == 0)
break;
}
return 0;
}
You can do this:
int main()
{
float number, sum=0.0f;
int index=0;
do
{
printf ("\t" "Enter number please.\n"); //Asking for a number from user
scanf("%f", &number); //Getting a number from a user
sum+=number; //Add number entered to the sum
i++;
} while (i < 3);
printf("Excellent, your average is %f\n", sum/3);
return 0;
}
#include <stdio.h>
#include <stdlib.h>
int main()
{
float f1,f2,f3;
char c='Y';
/* Program to calculate averages. */
/*Asks for the numbers.*/
do
{
printf(" Please enter three numbers.\n");
printf ("\t" "First number please.\n");
scanf("%f", &f1);
printf ("\t" "Second number please.\n");
scanf ("%f", &f2);
printf("\t" "Third number please.\n");
scanf("%f", &f3);
/* Now it averages it.*/
printf(" Thank you, wait one.\n");
printf(" Excellent, your sum is.\n");
printf("%f""\n", f1+f2+f3);
printf("Your average of the sum is now!!!!\n");
printf("%f", (f1+f2+f3)/3);
printf ("Do you wana continue [Y/N]...\n");
scanf("%c", &c);
}while(c!='N'&&c!='n');
return 0;
}

Resources