I have two functions, one for calculate the min and the max of an array the seconde one is for calculate the average of this array:
void find_min_max(double *tab, int nb, double *pmin, double *pmax) {
double val_min, val_max;
int i;
val_min = tab[0];
val_max = tab[0];
for (i = 0; i < nb; i++) {
if (tab[i] < val_min) {
val_min = tab[i];
} else
if (tab[i] > val_max) {
val_max = tab[i];
}
}
*pmin = val_min;
*pmax = val_max;
}
double find_average(double *tab, int nb) {
double average, sum;
int i;
sum = 0;
for (i = 0; i < nb; i++) {
sum = sum + tab[i];
}
average = sum / nb;
return average;
}
the array that I want to find the min, the max and the average of is a text file that contains floating point numbers:
int main() {
int i, j;
float tab[100] max, min, avg = 0;
FILE *mydata;
FILE *data_res;
f = fopen("data.txt", "r");
new_f = fopen("data_res.txt", "w");
if (mydata == NULL)
printf("Error");
else {
for (i = 0; i < n; i++)
fscanf(mydata, "%f", &tab[i]);
}
for (i = 0; i < 100; i++) {
for (j = i; j < 5; j++) {
fprintf(data_res, "%f ", tab[j]);
avg = find_average(tab);
find_min_max(tab, nb, &min, &max);
}
fprintf(new_f, "MAX = %lf\n", max);
fprintf(new_f, "MIN = %lf\n", min);
}
}
}
But the problem is it does not calculate the correct max and the correct min
There are multiple problems in your code:
n is not defined, the reading loop does not compile
you should test the return value of fscanf() to detect conversion errors and avoid undefined behavior.
you pass the address of float variables to functions that expect double pointers. You should use double for all values.
it is unclear why you use 1196 for the computing loop
it is unclear why you want to compute the average 5 values at a time.
you do not pass the size of the array in avg = find_average(tab);
you always compute the min and max of the first 5 values in find_min_max(tab, 5, &min, &max);
tab_C and b are not defined.
You must explain what you want the code to do with these values. As posted, it is unclear what your intent is from the reading the code.
To compute the running average, min and max, you should modify your code this way:
// compute the average of 5 elements starting at tab[i]
avg = find_average(tab + i, 5);
find_min_max(tab + i, 5, &min, &max);
Here is a modified version:
#include <stdio.h>
void find_min_max(const double *tab, int nb, double *pmin, double *pmax) {
double val_min, val_max;
val_min = val_max = tab[0];
for (int i = 1; i < nb; i++) {
if (tab[i] < val_min) {
val_min = tab[i];
} else
if (tab[i] > val_max) {
val_max = tab[i];
}
}
*pmin = val_min;
*pmax = val_max;
}
double find_average(const double *tab, int nb) {
double sum = 0.0;
for (int i = 0; i < nb; i++) {
sum += tab[i];
}
return sum / nb;
}
int main() {
int i, j;
double tab[1200], tab_C[1200], max, min, avg = 0, H, L, x = 0.2;
FILE *mydata;
FILE *data_res;
file = fopen("data.txt", "r");
data_res = fopen("data_res.txt", "w");
if (mydata == NULL || data_res == NULL) {
fprintf(stderr, "Cannot open files\n");
return 1;
} else {
for (i = 0; i < 1200; i++)
if (fscanf(mydata, "%lf", &tab[i]) != 1) {
fprintf(stderr, "Input error at index %d\n", i);
return 1;
}
}
for (i = 0; i < 1196; i++) {
//this loop is for taking 5 elements by 5
for (j = i; j < i + 5; j++) {
fprintf(data_res, "%f ", tab[j]);
}
fprintf(data_res, "\n");
avg = find_average(tab + i, 5);
find_min_max(tab + i, 5, &min, &max);
L = avg - ((avg - min) * b);
H = avg + ((max - avg) * b);
fprintf(data_res, "MAX = %f\n", max);
fprintf(data_res, "MIN = %f\n", min);
fprintf(data_res, "the average = %f\n", avg);
fprintf(data_res, "low value = %f\n", L);
fprintf(data_res, "High value = %f\n", H);
}
fclose(mydata);
fclose(data_res);
}
}
In find_min_max, try using this:
if (tab[i] > val_max)
{
val_max = tab[i];
}
instead of
else if (tab[i] > val_max)
{
val_max = tab[i];
}
Related
I need a program to evaluate Min, Max, Avg and Geometric avg of any number of integers. This is what I've come up with so far. Min and Max were working just fine until I added the Avg. Now Min and Avg is working right but Max gives wrong number (usually the second greatest number). Also geometric avg gives only 0.00000. Thanks for your help.
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
int main(int argc, char const *argv[]) {
int arr[100], max, i, min, size, lok = 1;
float arit = 0, geom = 0, sum = 0, prod = 0;
printf("\nSay how many integers you want to input: ");
scanf("%d", &size);
printf("\nType %d integers: ", size);
for (i = 0; i < size; i++) //put values in arr
scanf("%d", &arr[i]);
max = arr[0];
min = arr[0];
for (i = 1; i < size; i++) { //calc maximum
if (arr[i]>max) {
max = arr[i];
lok = i+1;
}
if (arr[i]<min) { //calc minimum
min = arr[i];
lok = i+1;
}
for (i = 0; i < size; i++) { //calc avg
sum = sum + arr[i];
}
arit = sum/size;
for (i = 0; i < size; i++) {
prod = prod * arr[i];
}
geom = pow(prod, 1./size);
}
printf("\n%d is maximum", max);
printf("\n%d is minimum", min);
printf("\n%f is avg", arit);
printf("\n%f is geometric avg", geom);
return 0;
}
The two main problems were
a misplaced closing } brace
wrong intialisation of prod = 0
I have made some other changes too:
check the validity of the inputs
use double instead of float (unless a good reason not to).
remove the unused lok
only one loop is needed for all the statistics
moved the position of the \n newlines as is customary.
This is the amended code:
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
int main(int argc, char const *argv[]) {
int arr[100], max, i, min, size;
double arit = 0, geom = 0, sum = 0, prod = 1; // init prod to 1
printf("\nSay how many integers you want to input: ");
if(scanf("%d", &size) != 1 || size < 1 || size > 100) {
exit(1); // or other action
}
printf("\nType %d integers:\n", size); // added newline
for (i = 0; i < size; i++) {
if(scanf("%d", &arr[i]) != 1) {
exit(1); // or other action
}
}
max = arr[0];
min = arr[0];
for (i = 0; i < size; i++) { // just one loop
if (arr[i] > max) {
max = arr[i];
}
if (arr[i] < min) {
min = arr[i];
}
sum = sum + arr[i];
prod = prod * arr[i];
}
arit = sum / size;
geom = pow(prod, 1.0 / size);
printf("%d is maximum\n", max); // reposition newlines
printf("%d is minimum\n", min);
printf("%f is avg\n", arit);
printf("%f is geometric avg\n", geom);
return 0;
}
This will fix your problem with Min and Max, and I guess also will fix geometric mean(check it) It was a problem closing for sentences
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
int main(int argc, char const *argv[]) {
int arr[100], max, i, min, size, lok = 1;
float arit = 0, geom = 0, sum = 0, prod = 1;
printf("\nSay how many integers you want to input: ");
scanf("%d", &size);
printf("\nType %d integers: ", size);
for (i = 0; i < size; i++) //put values in arr
scanf("%d", &arr[i]);
max = arr[0];
min = arr[0];
for (i = 1; i < size; i++) { //calc maximum
if (arr[i]>max) {
max = arr[i];
lok = i+1;
}
if (arr[i]<min) { //calc minimum
min = arr[i];
lok = i+1;
}
}
for (i = 0; i < size; i++) { //calc avg
sum = sum + arr[i];
}
arit = sum/size;
for (i = 0; i < size; i++) {
prod = prod * arr[i];
}
geom = pow(prod, 1./size);
printf("\n%d is maximum", max);
printf("\n%d is minimum", min);
printf("\n%f is avg", arit);
printf("\n%f is geometric avg", geom);
return 0;
}
About Geometric mean you are doing this.
float arit = 0, geom = 0, sum = 0, prod = 0;
and then
for (i = 0; i < size; i++) {
prod = prod * arr[i];
}
That allways will return 0 because you initialize prod at 0
The program is about finding the average temperature of all cities, but the result doesn't make sense (it is wrong)
I have tried splitting the program into functions for better understanding, but that didn't help me much.
#define amount_cities 5
#define amount_temp 3 // temp = temperature
int mintemp(int mas[amount_cities][amount_temp], int *index);
int maxtemp(int mas[amount_cities][amount_temp], int *index);
float avgtemp(int mas[amount_cities][amount_temp]);
int main(){
int arr_temp[amount_cities][amount_temp];
int i, j, ind;
// Set a temperatures for each city
for(i = 0; i < amount_cities; ++i){
printf("Temperature - city %d \n", i);
for(j = 0; j < amount_temp; ++j){
printf("Temperature %d - ", j+1);
scanf("%d", &arr_temp[i][j]);
}
}
for(i = 0; i < amount_cities; ++i){
printf("Temperature - city %ds \n", i);
for(j = 0; j < 3; ++j){
printf(" %d.- %d", j+1, arr_temp[i][j]);
}
printf("\n");
}
printf("Minimal temperature = %d ", mintemp(arr_temp, &ind));
printf("for city %d \n", ind);
printf("Maximal temperature = %d ", maxtemp(arr_temp, &ind));
printf("City %d \n", ind);
printf("Average temperature = %.2f\n", avgtemp(arr_temp));
return 0;
}
int mintemp(int mas[amount_cities][amount_temp], int *index){
int m, n, min_t;
min_t = mas[0][0];
*index = 0;
for(m = 0; m < amount_cities; ++m){
for(n = 0; n < amount_temp; ++n){
if(mas[m][n] < min_t){
min_t = mas[m][n];
*index = m;
}
}
}
return min_t;
}
int maxtemp(int mas[amount_cities][amount_temp], int *index){
int m, n, max_t;
max_t = mas[0][0];
for(m = 0; m < amount_cities; ++m){
for(n = 0; n < amount_temp; ++n){
if(mas[m][n] > max_t){
max_t = mas[m][n];
*index = m;
}
}
}
return max_t;
}
float avgtemp(int mas[amount_cities][amount_temp]){
int m, n;
float average_t = 0.0; // Average temperature
for(m = 0; m < amount_cities; ++m){
for(n = 0; n < amount_temp; ++n){
average_t += mas[m][n];
}
}
average_t /= amount_cities*mas[m][n];
return average_t;
}
I expected the output to be , 33.00 but got Average temperature = 30.00 instead.
I'm trying to write a function in order to solve a system of equations using the Gauss-Seidel method. The function I have so far doesn't do the job. The code stops giving me output after "Enter an initial guess..." and doesn't solve the function I'm inputting. Is this an issue with my function or some other part of my code?
/* code to solve a nxn system using the Gauss-Seidel method */
#include <stdio.h>
#include <math.h>
#include <stdlib.h>
#define MAX_DIM 100
#define MAX_ITER 500
#define TOLERANCE 1.e-6
void gauss_seidel(double a[][MAX_DIM], double b[], double x[], int n);
void main()
{
int i, j, n;
int violation_counter, answer;
int violation_rows[MAX_DIM];
double sum;
double a[MAX_DIM][MAX_DIM];
double b[MAX_DIM], x[MAX_DIM];
/* read in data */
n = MAX_DIM + 1;
while (n > MAX_DIM) {
printf("Enter the dimension of the system to be solved: ");
scanf_s("%d", &n);
}
printf("\n");
for (i = 0; i < n; i++) {
for (j = 0; j < n; j++) {
printf("Enter a[%d][%d] element of the system matrix: ",i,j);
scanf_s("%lf", &a[i][j]);
}
printf("Enter b[%d] of the right-hand-side vector: ", i);
scanf_s("%lf", &b[i]);
printf("\n");
}
/* test the convergence criterion */
violation_counter = 0;
for (i = 0; i < n; i++) {
sum = 0.0;
for (j = 0; j < n; j++)
if (i != j)
sum = sum + fabs(a[i][j]);
if (fabs(a[i][i]) < sum) {
violation_rows[violation_counter] = i;
violation_counter = violation_counter + 1;
}
if (a[i][i] == 0.0) {
printf("Found diagonal element equal to zero; rearrange equations; exiting ...\n");
exit(0);
}
}
if (violation_counter > 0) {
printf("The Gauss-Seidel convergence criterion is violated in %d rows out of %d\n", violation_counter, n);
printf("Specifically, it was violated in rows:\n");
for (i = 0; i < violation_counter; i++)
printf("%d ", violation_rows[i]);
printf("\n");
printf("Enter 1 if you want to continue; any other number to abort : ");
scanf_s("%d", &answer);
if (answer != 1)
exit(1);
printf("Check results carefully\n\n");
}
/* initialize the solution vector -- initial guesses */
for (i = 0; i < n; i++) {
printf("Enter an initial guess for x[%d] of the solution vector : ",i);
scanf_s("%lf", &x[i]);
}
/* solve the system */
gauss_seidel(a, b, x, n);
/* output solution */
for (i = 0; i < n; i++)
printf("x[%d]=%f\n", i, x[i]);
printf("\n");
}
/* function to solve a system using Gauss-Seidel */
void gauss_seidel(double a[][MAX_DIM], double b[], double x[], int n)
{
double maxerror = 1.0;
double iteration_error;
double e, sum, temp;
int i, j;
while (maxerror > 1.e-6) {
iteration_error = 0.0;
for (i = 0; i < n; i++) {
sum = 0.0;
for (j = 0; j < n; j++) {
if (i != j)
sum = sum + (a[i][j] * x[j]);
}
}
temp = (a[i][n] - sum) / a[i][i];
e = fabs((temp - x[i]) / x[i]);
x[i] = temp;
if (e > iteration_error)
iteration_error = e;
}
maxerror = iteration_error;
}
I made this code but I can't stop it. This code abou finding min, max, average values. What should I do?
#include <stdio.h>
void get_stat_per_test(int score[][3])
{
int i, k, min, max, sum;
for (k = 0; k<3; k++){
min = max = score[0][k];
sum = 0;
for (i = 0; i<10; i++){
if (score[i][k]<min) min = score[i][k];
if (score[i][k]>min) max = score[i][k];
sum += score[i][k];
}
printf("Max=%d\n", max);
printf("MIn=%d\n", min);
printf("Average=%f\n", sum / (3.0 * 10));
}
}
int main(void)
{
int i, k;
int score[10][3];
for (i = 0; i<10; i++){
for (k = 0; k<3; k++){
printf("The result is %d student in %d exam: ", i, k);
scanf("%d", &score[i][k]);
}
}
get_stat_per_test(score);
return 0;
}
After student 5 should stop.
EDIT II
I'm finally getting somewhere, now i get my random values with a return from the maxavg() function.
My only question now is, when i run the program i always get:
average: 0
maximum: 33
why? it does not make much sense.
Here is the new code:
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <limits.h>
int GetRand(int min, int max);
struct maxavg;
int main ()
{
int a[21][21], i , j, average, maximum, ret;
for (i = 0; i < 21; i++)
{
for ( j = 0; j < 21; j++)
{
a[i][j] = GetRand(0, 100);
printf("%3d" , a[i][j]);
}
a[2][15] = -1;
a[10][6] = -1;
a[13][5] = -1;
a[15][17] = -1;
a[17][17] = -1;
a[19][6] = -1;
printf("\n");
}
printf("average = %d \n maximum = %d", average, maximum);
return 0;
}
// random seed
int GetRand(int min, int max);
int get ()
{
int i, r;
for (i = 0; i < 21; i++)
{
r = GetRand(0, 100);
printf("Your number is %d \n", r);
}
return(0);
}
int GetRand(int min, int max)
{
static int Init = 0;
int rc;
if (Init == 0)
{
srand(time(NULL));
Init = 1;
}
rc = (rand() % (max - min +1) +min);
return (rc);
}
struct pair
{
int max;
int avg;
};
// max and average
struct pair maxavg()
{
struct pair p;
int max=INT_MIN, sum=0, count=0, avg, i, j, current;
for(i = 0; i < 21; i++){
for(j =0; j < 21; j++){
if(current > -1){
sum = sum + current;
count = count + 1
;if(current > max){
max = current;
}
}
}
}
avg = sum/count;
printf("Max is %d \n", max);
printf("Average is %d \n", avg);
p.max = max;
p.avg = avg;
return p;
}
EDIT:
So here is what i'm doing, i get error messages:
Average:
// Average Code
value = a[i][j];
int actualvalue, suma = 0, quant;
for(i=0; i<21; i++){
for(j=0; j<21; j++){
if (actualvalue > -1){
a[i][j] = actualvalue;
suma = suma + actualvalue;
// sum actual value + nextvalue (sum of all > -1) //
}
else if {
quant = quant + 1;
//(sum the quantity of times a value has been greater than -1)//
}
}
}
printf("The average value is:", suma/quant); ///(sun of all values > -1)/(sum of quantity value was > -1)/
Find Maximum:
// Max
int variableP = a[0][0];
value = a[i][j];
int variableP = a[i][j]
for(i=0; i<21; i++){
for(j=0; j<21; j++){
if(variableP < newvalue){
variableP = newvalue
}
}
}
printf("The max value of the 2D array is", %d);
Average and Maximum:
// max and average
int maxvg();
int max=INT_MIN, sum=0, count=0, avg;
for(i = 0; i < 21; i++){
for(j =0; j < 21; j++){
if(current > -1){
sum = sum + current;
count = count + 1
if(current > max){
max = current;
}
}
}
}
avg = sum/count;
printf("Max is %d \n", max);
printf("Average is %d \n", avg);
So how right or wrong is this? what am i missing.
i mostly get:
[Error] expected '=', ',', ';', 'asm' or '__attribute__' before '<' token
[Warning] data definition has no type or storage class
[Error] initializer element is not constant
[Error] expected declaration specifiers or '...' before string constant
Am i at least close to it?
Thanks in advance.
END OF EDIT
I created a 2D array with random numbers from 0 to 100 (and a couple of -1) values with this code:
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
int main ()
{
int a[21][21], i, j;
for (i = 0; i < 21; i++) {
for (j = 0; j < 21; j++) {
a[i][j] = GetRand (0, 100);
a[7][15] = -1;
a[10][6] = -1;
a[13][5] = -1;
a[15][17] = -1;
a[17][17] = -1;
a[19][6] = -1;
printf ("%3d", a[i][j]);
}
printf ("\n");
}
return 0;
}
// random seed
int GetRand (int min, int max);
int get ()
{
int i, r;
for (i = 0; i < 21; i++) {
r = GetRand (0, 100);
printf ("Your number is %d \n", r);
}
return (0);
}
int GetRand (int min, int max)
{
static int Init = 0;
int rc;
if (Init == 0) {
srand (time (NULL));
Init = 1;
}
rc = (rand () % (max - min + 1) + min);
return (rc);
}
This prints the array created. Now I want to calculate the maximum value of all values inside the array and the total average of all values in the array, all while ignoring all -1 values, so only from 0 to 100. Since I'm a total beginner I'm having problems creating these functions. So here are my ideas.
//For the average
for(i=0; i<1; i++){
for(j=0; j<21; j++){
if (actualvalue > -1){
//sum actualvalue + nextvalue (sum of all the values greater than -1)//
}
else if (actualvalue > -1){
//(sum the quantity of times a value has been greater than -1)//
}
}
}
}
printf("The average value is", //(sum of all values>-1)/(sum of quantity value was >-1) //);
I'm representing the thing i don't know how to write in code in words so you get my idea.
Now for finding the maximum: what i think i should do is initialize the array and make a variable adopt the first value it finds that's > -1, then rewind and initialize again, if the actualvalue < newvalue then make variableP adopt the newvalue:
//max
int variableP = a[i][j]
for(i=0; i<21; i++){
for(j=0;j<21;j++){
if(variableP < newvalue){
variableP = newvalue
}
printf("The max value of the 2D array is", %d);
}
I know it's evident i'm not sure what i'm writing here, but i think my idea of it is correct, i hope i'm explaining it well enough.
Sum is as you say.
Average requires you count number of >-1 values.
Max looks right lines. Finish off your ideas and ask again if it doesn't work
You can do both max and avg in one loop.
Declare three variables: max=-999999, sum=0, count=0.
Each time when current cell is not -1 increase sum by it's value and count by 1.
Each time check if current value is bigger than max, then set max to current value.
After the loop is done, avg = sum/count.
Consider you are doing all your arithmetic using integers, and integer division is integer. Perhaps you have better to do a double result with:
/* you don't actually need to cast to double in both operators, as the
* one not casted will be automagically casted to double to operate on.
*/
double average = (double) sum_of_samples / (double) number_of_samples;
You have to cast at least one of the operators, because if you don't you'll get the result as before (a 0 integer result) converted to double to assign to the variable.