Proteincalculator with algebra - c

Im trying to make this protein-calculator (in C language) to work but it doesn't work:
#include <stdio.h>
#include <stdlib.h>
int main()
{
double proteinhalt[20];
double proteinmangdtot[20];
double kottfiskmengdtot;
printf("Enter proteinhalt / 100 gram: ");
fgets(proteinhalt, 20, stdin);
printf("Enter proteinmangd att konsumera idag (gram): ");
fgets(proteinmangdtot, 20, stdin);
kottfiskmengdtot = ((double)proteinmangdtot/(double)proteinhalt)*100;
printf("Du behöver %f gram.", kottfiskmengdtot);
}
The error is:
Line 13 error: pointer value used where a floating-point was expected
What is wrong?
Edit: In english:
#include <stdio.h>
#include <stdlib.h>
int main()
{
double proteinpercentage[20];
double proteinamounttot[20];
double meatfishamounttot;
printf("Enter proteinpercentage / 100 gram: ");
fgets(proteinpercentage, 20, stdin);
printf("Enter protein amount to consume today (gram): ");
fgets(proteinamounttot, 20, stdin);
meatfishamounttot = ((double)proteinamounttot/(double)proteinpercentage)*100;
printf("You need %f gram.", meatfishamounttot);
}

You have two errors.
fgets, expects a character array as argument, but you specify an array of doubles
at the assignment of meatfishamounttot, you cast an array of doubles to a double
Solution (simplified, no error checking):
char str[20];
double proteinpercentage;
double proteinamounttot;
double meatfishamounttot;
// read at most 20 characters from stdin
fgets(str, 20, stdin);
// convert the string to a double
proteinpercentage = strtod(str, NULL);
fgets(str, 20, stdin);
proteinamounttot = strtod(str, NULL);
meatfishamounttot = (proteinamounttot / proteinpercentage) * 100;

This is how the program should work:
#include <stdio.h>
#include <stdlib.h>
#include <stddef.h>
int main()
{
char str[20];
double proteinpercentage;
double proteinamounttot;
double meatfishamounttot;
printf("Enter proteinpercentage / 100 gram: ");
fgets(str, 20, stdin);
proteinpercentage = strtod(str, NULL);
printf("Enter protein amount to consume today (gram): ");
fgets(str, 20, stdin);
proteinamounttot = strtod(str, NULL);
meatfishamounttot = (proteinamounttot / proteinpercentage) * 100;
printf("You need %f grams.", meatfishamounttot);
}

Related

Implementing two sample t-test in C

I am making a function that will calculate the test statistic from a two sample t-test and return it's value. However, I have been getting incorrect results. I previously was using scanf and got good answers, but it randomly stopped working. So I decided to switch to fgets which is suppose to be more reliable, however, the values it's returning are incorrect.
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#define VAL 10
double tstat(int x1,int x2,int s1,int s2,int n1,int n2);
int main()
{
char mean1[VAL] = {0};
char sd1[VAL] = {0};
char n1[VAL] = {0};
char mean2[VAL] = {0};
char sd2[VAL] = {0};
char n2[VAL] = {0};
printf("Enter mean 1: \n");
fgets(mean1, 10, stdin);
printf("Enter sd 1: \n");
fgets(sd1, 10, stdin);
printf("Enter sample size 1: \n");
fgets(n1, 10, stdin);
printf("Enter mean 2: \n");
fgets(mean2, 10, stdin);
printf("Enter sd 2: \n");
fgets(sd2, 10, stdin);
printf("Enter n2: \n");
fgets(n2, 10, stdin);
printf("t value is: %lf", tstat(atoi(mean1),atoi(mean2),atoi(sd1),atoi(sd2),atoi(n1),atoi(n2)));
}
double tstat(int x1,int x2,int s1,int s2,int n1,int n2)
{
double t = 0;
t = (x1 - x2)/(sqrt(pow(s1,2)/n1+pow(s2,2)/n2));
return t;
}
For example, setting mean1 = 1.3, sd1 = 0.5, n1 = 22; mean2 = 1.6,sd2 = 0.3, n2 = 24 should yield a value of -2.44, however, plugging this in returns -1 followed by #IND00. I presume my issue is that either I am misinterpreting how to properly use fgets, or something is going wonky with the datatypes, though I am a beginner in C, and I have not been able to spot any clear errors.
Your variables are all of type int and you're using atoi to convert the strings to int. However, the values you're entering aren't integers, they're floating point values, so only the integer part of each number is interpreted. For example, atoi("1.3") results in 1.
You need to change your datatypes to double and use atof instead.
double tstat(double x1, double x2, double s1, double s2, double n1, double n2)
{
double t = 0;
t = (x1 - x2)/(sqrt(pow(s1,2)/n1+pow(s2,2)/n2));
return t;
}
...
printf("t value is: %lf", tstat(atof(mean1),atof(mean2),atof(sd1),atof(sd2),atof(n1),atof(n2)));

How to make code say 'invalid input' when a user enters a character or a string (Validate)

I'm new to c and i just wanted to know how to make my code say ' invalid input' if they decide to enter a character or gibberish.
My code is just a simple Celsius to Kelvin (i know very simple) and i just adds 273 to any inputted number. i tried to use isdidgit but it was unsuccessful.
My code;
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <ctype.h>
int temp = 273;
int cel;
int cel2;
int choice;
switch (choice)
{
case 1:
printf("enter ce to conv to kel: ");
scanf("%ld", &cel);
cel2 = cel + temp;
printf("%d in Celsuis is: %d Kelvin \n", cel, cel2)
I accept all feedback / improvements,
thanks
~Neamus
Presently, your code has no way to recover from an invalid input. That is, if a user enters "a" when prompted, scanf() will never return because it will be waiting for a base-10 integer value.
What you will need to do is read the input as a C-string and process that:
char input[80];
do {
printf("enter ce to conv to kel: ");
scanf("%79[^\n]\n", input); // read until newline; toss newline
} while (input_is_bad(input)); // your function to validate input
cel = atoi(input); // atoi parses C-string, returning an int
cel2 = cel + temp;
printf("%d in Celsuis is: %d Kelvin \n", cel, cel2);
Inside your own input_is_bad() function, you can print a message stating that the input is not valid.
You can achieve this by using fgets and strtol. See the following code:
#include<stdio.h>
#include <stdlib.h>
int main()
{
int temp = 273;
int cel;
int cel2;
int choice;
int flag;
char *p, str[100];
printf("enter ce to conv to kel: ");
while (fgets(str, sizeof(str), stdin)) {
cel = strtol(str, &p, 10); //number of base 10
if (p == str || *p != '\n') {
printf("Please enter an integer: ");
}
else break; //if input is integer then break the loop
}
//do your calculations here
return 0;
}

Converting integer to string with atoi/sprintf

This is not my whole code I just sum it up to be easy to see. I have no problem to convert the string into an integer but I cannot convert the integer into a string.
The program just crashes. Here is the code. Look at the line with itoa.
#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
#include <string.h>
#define SIZEX 49
#define SIZEY 6
int main() {
size_t x, y;
char *a[50][7];
char name[50][100];
char surname[50][100];
char IN[50][100];
char YOB[50][100];
char usname[50][100];
char pass[50][100];
char totamount[50][100];
for (x = 0; x <= SIZEX; x++) {
a[x][0] = name[x];
a[x][1] = surname[x];
a[x][2] = IN[x];
a[x][3] = YOB[x];
a[x][4] = usname[x];
a[x][5] = totamount[x];
a[x][6] = pass[x];
}
printf("\nPlease enter the name of the new user\n");
scanf(" %s", a[0][0]);
printf("Please enter the surname of the new user\n");
scanf(" %s", a[0][1]);
printf("Please enter the Identity Number of the new user\n");
scanf(" %s", a[0][2]);
printf("Please enter the year of birth of the new user\n");
scanf(" %s", a[0][3]);
printf("Please enter the username of the new user\n");
scanf(" %s", a[0][4]);
strcpy(a[0][6], a[0][4]);
strrev(a[0][6]);
a[0][5] = "0";
int z;
z = atoi(a[0][5]);
z = z + strlen(a[0][4]) * 10;
itoa(z, a[0][5], 10);
//sprintf(a[0][5], "%d", z);
printf("%s\n", a[0][5]);
printf("%d\n", z);
return 0;
}
By doing this:
a[0][5]="0";
You are assigning to a[0][5] a pointer to a readonly memory containing string literal "0".
Here:
itoa( z, a[0][5],10 );
you are attempting to write there, giving you memory access violation.

Scanf is being ignored [duplicate]

This question already has answers here:
Simple C scanf does not work? [duplicate]
(5 answers)
Closed 7 years ago.
#include <stdio.h>
#define length 20
main()
{
float x;
int y;
float array1[length], array2[length], array3[length];
float ray[length];
int size1 = insert(array1, length);
printf("enter number: ");
scanf("%d", &y);
int size2 = insert(array2, length);
int size3 = insert(array3, length);
}
int insert(float a[], int size)
{
int n = 0;
while(n<size && scanf("%f\n", &a[n]) == 1)
{
printf("you entered: ");
printf("%2.1f\n", a[n]);
n++;
}
return n;
}
When I run the program, it executes the first insert okay, but the next time function is called, scanf() seems to be ignored completely. I tried putting it right after where insert is done, but that's ignored as well.
Use %*c in scanf to consume the newlines along with space around %d in the scanf in main(). I tested the below code on MingW and it seem to work. The '\n' in your scanf is being consumed making it scanf() return while the '\n' at the press of enter key still remains in IO buffer to be consumed by scanf() again; hence the weird behaviour.
#include <stdio.h>
#include <stdlib.h>
#define length 20
int insert(float *a, int size)
{
int n = 0;
while(n<size && scanf("%f%*c", &a[n]))
{
printf("you entered: ");
printf("%2.1f\n", a[n]);
n++;
}
return n;
}
int main(int argc, char* argv[])
{
float x;
int y;
float array1[length], array2[length], array3[length];
float ray[length];
int size1 = insert(array1, length);
printf("enter number: ");
scanf("%d", &y);
int size2 = insert(array2, length);
int size3 = insert(array3, length);
return 0;
}
In the scanf format string, change "%f\n" to "%f". The \n in a scanf format string does not mean "wait for newline".
You do not need to worry about waiting for newline, because the only format specifiers you use are %f and %d, which both discard any leading whitespace.

How to limit user to input a float with one decimal point in C

Program to limit the user's input to one decimal point in C.
For example:
Enter grade: 5 //Acceptable
Enter grade: 8.5 //Acceptable
Enter grade: 6.467 //Not acceptable, Re-enter grade
#include <stdio.h>
#include <math.h>
main()
{
double grade[8];
int i;
for (i = 0; i < 8; i++) {
printf("Insert grade: ");
scanf("%f", &grade[i]);
}
}
You will have to input the data as string, then check it only has one decimal place.
It is not possible to input a floating-point value and then check for decimal places; since the floating point values are stored internally with binary places and hold an approximation of the value that was input, in most cases.
The input code could look like:
char temp[20];
if ( 1 != scanf("%19s", temp) )
return EXIT_FAILURE;
// code to check for decimal place goes here - I'm purposefully not
// showing it as this looks like homework!
// once we have checked that the input is correct, then convert to double
grade[i] = strtod(temp, NULL);
#include <stdio.h> // printf(), scanf()
#include <math.h> // floor()
main()
{
double grade[8];
int i;
for (i = 0; i < 8; i++)
{
do
{
printf("Insert grade: ");
scanf("%lf", &grade[i]);
grade[i] *= 10;
if (grade[i] != floor(grade[i])) // Prints error message, if user types more than one decimal point
{
printf("Grade must have one decimal point.\nPlease re-enter grade.\n");
}
}while (grade[i] != floor(grade[i])); // Checks decimal point
}
}
Use fgets() to read the line into a buffer and then test that buffer.
char buf[99];
fgets(buf, sizeof buf, stdin);
// parse the line as a float - look for problems
char *endptr;
float f = strtof(buf, &endptr);
if (buf == endptr || *endptr != '\n') Fail_NonFloatInput();
// look for .
char *dot = strchr(buf, '.');
if (dot && isdigit(dot[1]) && isdigit(dot[2])) Fail_TooMuchPrecisison();
}
Alternatively code could try:
long long i;
int f;
if (2 != scanf("%lld.%1d", &i, &f)) Bad_Input();
float fl = i + f/10.0;
But that fails float input like 123456789012345678901234567890.0.
As #Matt McNabb says, read as text first.
You can use printf format specifiers to specificy the number of positions you are interested.
A format specifier follows this prototype: [see compatibility note below]
%[flags][width][.precision][length]specifier
Example from the cplusplus.com
#include <stdio.h>
int main()
{
printf ("floats: %4.2f %+.0e %E \n", 3.1416, 3.1416, 3.1416);
return 0
}
Output
floats: 3.14 +3e+000 3.141600E+000
More examples here http://www.cplusplus.com/reference/cstdio/printf/

Resources