0

I just started to learn C from absolute zero.

I have a task to solve function y = f(x) by putting in x values - function is given in my code. Total x and y values are 15(from 0 to 14). First of all, I ask about x0 - start x value and then I ask about what STEP is going to be

(take a look at code)

1st for loop:

For x values, logic should look like this(START is variable for x0 - means first value):

1) START
2) START + STEP
3) START + 2*STEP
4) START + 3*STEP
.
.
.
15) START + 15*STEP

2nd for loop:

Here I am trying to put in my x values into f(x) function.


So here are 2 problems:

  • 1st problem is that when we take different START(x) values and STEPS some of them making the answer as the infinite number like x=4 and the program just crashes.
  • 2nd problem I don't know why, but neither float nor double doesn't show answer as a floating-point value. Like if we put x=2, so y = 39.5 and the program shows it like 39.00.

Tried to change float or double, counters and different variables. Actually, I think I just have a lack of experience

Here's wolfram alpha to check different values: https://www.wolframalpha.com/input/?i=(14*x%5E3%2B7*x%5E2-2%2B20)%2F(x%5E2-4*x),+x%3D5

Compiler: Geany

#include <stdio.h>
#include <math.h>
#define MAX 14




int main()
{

    int i,j;            // counter
    int START;          // x0
    int STEP;           // 
    int x[MAX];         // x values array - total 15
    double y[MAX];      // f(x) values - total 15

    printf("START NUMBER: ");
    scanf("%d",&START);
    printf("\n");

    printf("STEP: ");
    scanf("%d",&STEP);
    printf("\n");

    /* This cycle is for calculating x values until 15(from 0 to 14)
    * Using logic of a homework it should be like this:
    * First value 1) x0; 2) x0 + STEP; 3) x0 + 2*STEP; 4) x0 + 3*STEP and etc
         */
    for(i=0;i <= MAX; i++)
    {
        x[i] = START + (STEP*i);
        /* printf to check if it counts at all: */ printf("%d\n",x[i]);
    }

    printf("\n");
    /* This cycle is for calculating y(function) values using array of x's
    * function y =   (14x^3 + 7x^2 - x + 20)
    *               ------------------------
    *                       (x^2 - 4x)
    */
    for(j=0;j <= MAX; j++)
    {
        y[j] = ((14*(x[j])*(x[j])*(x[j]) + 7*(x[j])*(x[j]) - x[j] + 20)/(x[j]*(x[j]) - 4*x[j]));
        /*  printf to check if it counts at all:*/ printf("%.2lf\n",y[j]);
    }



    return 0;

    }

I just want to make for a second for cycle to avoid infinite values and put it in y array, like just 0 instead of crashing after an infinite value, I think it could be done by if cycle, but I don't know how to put it logically into for loop, so for could just continue to solve in peace and if works as сhecker.

And the second thing is about floating-point. I just don't actually understand why if I put into f(x), x=2 it gives me 39.00, not 39.50 like wolfram did.

  • 3
    How about to start with simpler math to understand how types and arithmetics work in C? All your calculations are done on integer type, this is why you are getting your results rounded here and there. – Eugene Sh. Aug 15 '19 at 16:24
  • 1
    Possible duplicate of [What is the behavior of integer division?](https://stackoverflow.com/questions/3602827/what-is-the-behavior-of-integer-division) – Code-Apprentice Aug 15 '19 at 16:29
  • For problem #2, you have encountered integer division. See the link above for an explanation. – Code-Apprentice Aug 15 '19 at 16:29
  • For problem #1, please show an example of what you enter as START and STEP. – Code-Apprentice Aug 15 '19 at 16:32

1 Answers1

1

Your issue with the program printing 39.00 instead of 39.50 comes from the fact that you are using integer operations.
See Can integer division in C/C++ run into loss of precision issues?.
The lazy way to solve this issue would be to replace int x[MAX]; by float x[MAX];
Also, in for(i=0;i <= MAX; i++) & in for(j=0;j <= MAX; j++) you run the loops 15 times instead of 14 and create a buffer overflow (because you access x[14] and y[14]).
You also have a nasty division by 0 in there.
I tried to improve your code:

#include <stdio.h>
#include <math.h>
#define MAX 14

int main()
{
    int i,j;
    int START, STEP; 
    double y[MAX], x[MAX];

    printf("START NUMBER: ");
    scanf("%d", &START);
    printf("STEP: ");
    scanf("%d", &STEP);

    printf("counted:\n");
    for(i = 0; i < MAX; i++)
    {
        x[i] = START + (STEP * i);
        printf("%.0lf\n", x[i]);
    }
    printf("Results: \n");
    for(j=0;j < MAX; j++)
    {
        if (pow(x[j], 2) == 4 * x[j]) //prevent division by 0, if(x==4) also works
            y[j] = NAN; //the solution doesn't exist
        else
            y[j] = (14 * pow(x[j], 3) + 7 * pow(x[j], 2) - x[j] + 20)
                / (pow(x[j], 2) - 4 * x[j]);
        printf("%.2lf\n", y[j]);
    }
    return 0;
}

Note that I use pow() but you can use your own function (and it would be faster).

  • Huge thanks to you. I am kind of sad, that I didn't notice division by 0. About looping 15 times. In the task, I must loop no more than 15 times, so `MAX` is 14 because in `for` loop I'm using a counter that starts from 0. By that I mean from 0 to 14 is 15 actually. Isn't it right? – Alexey Kozlov Aug 16 '19 at 05:28
  • Yes, looping from 0 to 14, *14 included* is looping 15 times. If you actually want to loop 15 times (and so have 15 x and 15 y values), just set `MAX` to 15. Remember, arrays start at 0 and C won't warn about overflows. – Arthur Woimbée Aug 16 '19 at 11:18