Happy Pi Day!
It's Pi Day! The ratio of a circle's circumference to its diameter—an irrational number, with its infinite number of digits—seems to hold a special place in the hearts of many.
0. Video Warm-Ups
1. Calculate Pi (recursively or with a loop)
Write a program that finds and outputs a calculated value of pi using recursion and the following series:
(π2)/6 = 1 + 1/22 + 1/32 + ... + 1/n2
The value n is the number of iterations of the recursion. Your main program will ask for a value n, and then call your recursive function to calculate the sum of the series. With that sum, the main program can then calculate the value of pi.
Finally, compare that calculated value with the value of pi available in the math library (Math.PI
for Java, math.pi
for Python). What is the percent difference between your calculated value and the actual value in the library? How many iterations (n) does it take your program to get to within 0.1% of the actual value of pi?
(Python solution)
2. Read the digits of pi into a program
To be able to study the digits of pi, we need to be able to read them into a program. This text file contains the first million decimal places of pi.
Right-click or control-click on the link to download that file onto your computer. Then open that file and read its digits into a program using one of the utility functions given here.
Show/hide Java code
import java.util.ArrayList;
import java.util.Scanner;
import java.io.FileNotFoundException;
import java.io.File;
/**
* This method takes a text file and imports it line by line into
* an ArrayList<String>
* NOTE THAT ALL CODE USING THIS METHOD MUST ALSO THROW A
* FileNotFoundException!
* See code below for an example.
*
* @param filename a text file to be imported
* @return an ArrayList<String>, with each element of the array a line from the file
*/
public static ArrayList<String> importFile(String filename) throws FileNotFoundException
{
File f = new File(filename);
Scanner in = new Scanner(f);
ArrayList<String> lines = new ArrayList<String>();
while (in.hasNext())
lines.add(in.nextLine());
return lines;
}
Show/hide Python code
def get_data_as_file(filename):
"""Reads a text file `filename` and places the entire contents
in a single variable.
"""
infile = open(filename,'r') # opens filename for reading
file_contents = infile.read() # gets entire value as a string
infile.close()
return file_contents
def get_data_as_lines(filename):
"""Reads a text file `filename` line by line, and places each line
in a list.
"""
infile = open(filename,"r")
lines = []
for line in infile:
lines.append(line.rstrip()) # gets rid of \n at end of each line
infile.close()
return lines
3. Count the digits of pi
Are the digits 0-9 evenly represented in those digits? Are there more 1s than 2s, or more 7s then 6s?
Write a program to import that text file and count the frequency of each digit.
Note for Java: You can convert a String-based integer—7, for example—to an Integer using the Integer.parseInt() method:
String stringNum = "12345";
int num = Integer.parseInt(stringNum);
4. Find your birthdate in pi
There are lot of numbers in an infinite sequence. Like... infinitely many.
Take the two-digit forms of your birth month and date to make a string of values—mine is Feb 8, or 0208
—then determine where in the value of pi that string occurs.
The birthdate that appears earliest in the sequence wins!
5. Calculate Pi using the Chudnovsky algorithm
You'll need to do some research on how to do this... or you can just read about the Chudnovsky Brothers in this New Yorker article and try running one of the programs shown here.
These are "generators" that don't produce a single value at the end of solving the problem. Instead they iterate through the problem, producing a single digit at a time and display it on the screen as it goes.
Show/hide Java code
import java.math.BigInteger ;
public class PiBigInteger {
final BigInteger TWO = BigInteger.valueOf(2) ;
final BigInteger THREE = BigInteger.valueOf(3) ;
final BigInteger FOUR = BigInteger.valueOf(4) ;
final BigInteger SEVEN = BigInteger.valueOf(7) ;
BigInteger q = BigInteger.ONE ;
BigInteger r = BigInteger.ZERO ;
BigInteger t = BigInteger.ONE ;
BigInteger k = BigInteger.ONE ;
BigInteger n = BigInteger.valueOf(3) ;
BigInteger l = BigInteger.valueOf(3) ;
public void calcPiDigits(){
BigInteger nn, nr ;
boolean first = true ;
while(true){
if(FOUR.multiply(q).add(r).subtract(t).compareTo(n.multiply(t)) == -1){
System.out.print(n) ;
if(first){System.out.print(".") ; first = false ;}
nr = BigInteger.TEN.multiply(r.subtract(n.multiply(t))) ;
n = BigInteger.TEN.multiply(THREE.multiply(q).add(r)).divide(t).subtract(BigInteger.TEN.multiply(n)) ;
q = q.multiply(BigInteger.TEN) ;
r = nr ;
System.out.flush() ;
}else{
nr = TWO.multiply(q).add(r).multiply(l) ;
nn = q.multiply((SEVEN.multiply(k))).add(TWO).add(r.multiply(l)).divide(t.multiply(l)) ;
q = q.multiply(k) ;
t = t.multiply(l) ;
l = l.add(TWO) ;
k = k.add(BigInteger.ONE) ;
n = nn ;
r = nr ;
}
}
}
public static void main(String[] args) {
PiBigInteger p = new PiBigInteger() ;
p.calcPiDigits() ;
}
}
Show/hide Pi code
#!/usr/bin/env python3
"""
From http://rosettacode.org/wiki/Pi#Python
"""
def calcPi():
q, r, t, k, n, l = 1, 0, 1, 1, 3, 3
while True:
if 4*q+r-t < n*t:
yield n
nr = 10*(r-n*t)
n = ((10*(3*q+r))//t)-10*n
q *= 10
r = nr
else:
nr = (2*q+r)*l
nn = (q*(7*k)+2+(r*l))//(t*l)
q *= k
t *= l
l += 2
k += 1
n = nn
r = nr
import sys
pi_digits = calcPi()
i = 0
for d in pi_digits:
sys.stdout.write(str(d))
i += 1
if i == 40: print(""); i = 0