2

I have been trying for a few days to compute pi using the series expansion pi = 4(1-1/3+1/5-1/7... but whenever I use the code I have below, it returns 4.0.

public class Pi {
    public static void main (String args[]) {
        double pie = 0.0;
        int max = 1000;
        for (int x = 1 ; x < max ; x = x + 2) {
            if (x % 4 == 1) {
                pie+= 1/x;
            } else if (x % 4 == 3) {
                pie-=1/x;
            }
        }
        System.out.println(4*pie);
    }
}

In this, I am computing pie to a denominator below 1000. Pie is the variable that stores my value created for pie. At the end, it prints pi, but always returns 4.0.

Using the Debug feature in my IDE (Eclipse), I see the value of pie jumps to 4 from the initial value of 0, but then does not change for the rest of the times the program increments the value of x in the for loop, it does not do anything to pi.

mpromonet
  • 11,326
  • 43
  • 62
  • 91
Rohit M
  • 21
  • 1

3 Answers3

4

You are performing integer division with 1/x, which always results in an int, truncating the true decimal value. 1/1 is 1, but 1 divided by anything larger is 0 in Java, so your result will always be 4.

Use a double literal to force floating-point division.

pie += 1.0 / x;  // and pie -= 1.0 / x;

Alternatively, you can cast 1 to a double.

pie += (double) 1 / x;  // and pie -= (double) 1 / x;
rgettman
  • 176,041
  • 30
  • 275
  • 357
1

The problem is that you are performing integer division and adding the result to a double. x is an int and 1 is an int. When you divide an integer by an integer, you get back an integer. Hence what you're adding to pie is always an integer.

The first time you run the loop, you evaluate the expression 1/1, which returns just 1 (an integer) and assigns that value to pie. For everything else after, you get 0, which means that pie doesn't change. Hence when you finally print 4 * pie, you get 4.

There are a few options:

  • Use double everywhere.
  • Change pie += 1 / x; to pie += (1.0 / x); (and the same for the other one)
  • Cast 1 to double before adding to pie: pie += (double) 1 / x.
Vivin Paliath
  • 94,126
  • 40
  • 223
  • 295
  • 1
    With all the `code` emphasis, this is a bit `annoying` to read. – eis Jul 02 '15 at 17:34
  • I find it enhances readability. I like to call out variables and keywords by using `code`. – Vivin Paliath Jul 02 '15 at 17:34
  • Yeah, but doing it everywhere means you call attention to everything, thus setting nothing apart. rgettman's answer is much easier to read, since the actual code is formatted on its own line. Though, I only voted for his over yours since it was posted first. – mbomb007 Jul 02 '15 at 17:38
  • I'm not sure using it on `x`, `int`, and expressions like `1/1` translates to using it "everywhere". Perhaps I could have reworded my answer so that usages aren't so close together. Also the usage of `code` in rgettman's answer isn't just limited to the actual code examples - he uses it in regular text too. – Vivin Paliath Jul 02 '15 at 17:41
0

The problem is that you are making an integer division which returns less than zero. As an integer, the value will be rounded to zero instead. This adds zero to pie on each iteration.

What you need to do is to replace the literal integer ones, to literal floating point ones, like this

package cl.misc.pi;

public class Pi {
    public static void main(String args[]) {
        double pie = 0.0;
        int max = 1000;
        for (int x = 1; x < max; x = x + 2) {
            if (x % 4 == 1) {
                pie += 1.00 / x;
            } else if (x % 4 == 3) {
                pie -= 1.00 / x;
            }
        }
        System.out.println(4 * pie);
    }
}

As you see, I did replace pie += 1 / x for pie += 1.00 / x which now adds a floating point result to pie.

Result of this routine is 3.139592655589785

Cristian Meneses
  • 4,013
  • 17
  • 32