Homework #3

Due: Friday, Feb. 20

Chapter 3: Memoization Binomial coefficient Program (see below), Exercises 5 (show D(k) arrays), 19, 20, 26 (trace steps like I did on the chalk board), 34 (write a program and should output from test cases)

Memoization Program for Binomial Coefficient

Problem: Using the memoizaton technique discussed in class, write a program to calculate the binomial coefficient.

Recall that the memoization method is a form of dynamic programming so that you calculate each "smaller" problem instances once and store their results for future usage if you need it. However, the code you write will look very much like the divide-and-conquer program, but instead of always just performing the recursive calls, you check to see if the problem has previously been solved. If is has, using the stored solution and avoid the recursive call. Since the code is written recursively and is called initially with the "largest" problem that you want to solve, your program will not waste time solving "smaller" problems that do not contribute to the solution of the "largest" problem.

In general memoization algorithms are split into two subprograms:

1) The first subprogram initializes the space(i.e., array) used to store the results to either some "UNCALCULATED" value or base case values. Then it calls the second subprogram to actual perform the calculation. After the second subprogram returns, the "largest" result of interest is returned.

2) The second subprogram does the work in "top-down" fashion as described above.

See the fibonacci programs as examples.

Hand in:

a) A paper copy of your program. Your program should be reasonably documented (have comments) and conform to a reasonable style.

b) Sample output demonstrating your program. Include the example of "picking 6 of 10 items". Your output should include not only the number of combinations, but also all values stored in the array since we want to highlight that calculating the results of some "smaller" problems was avoided using memoization.

/******************* fibonacci_mem.cpp ***********************

Programmer: Mark Fienup

Description: This program calculates fibonacci using memoization. Memoization solutions look like divide-and-conquer algorithms in that they are recursive, but avoid recomputation of redundant subproblems by checking to see if the solution to a subproblem has been previously computed before performing a recursive call. The previously calculated subproblems are stored in an array similarly to dynamic programming algorithms.

**************************************************************/

#include <iostream.h>

#include <stdlib.h>

#include <iomanip.h>

const long UNCALCULATED = -1;

// Prototypes:

long CalculateFibonacci(long n);

long MemorizeFibonacci(long n, long fibonaccis[]);

int main(int argc, char * argv[]) {

long n;

long result;

if (argc != 2) {

cerr << "Usage: " << argv[0] << " n" << endl;

exit(1);

} // end if (argc..

n = atol(argv[1]);

result = CalculateFibonacci(n);

cout << "The " << n << "th fibonacci number is "

<< result << endl;

return 0;

} // end main

long MemoizeFibonacci(long n, long fibonaccis[]) {

if (fibonaccis[n] == UNCALCULATED) {

fibonaccis[n] = MemoizeFibonacci(n-1, fibonaccis)

+ MemoizeFibonacci(n-2, fibonaccis);

} // end if

return fibonaccis[n];

} // end MemoizeFibonacci

// Performs the initialization and then calls the recursive

// memoization function

long CalculateFibonacci(long n) {

long results;

long i;

long * fibonaccis = new long [n+1];

fibonaccis[0] = 0;

fibonaccis[1] = 1;

for (i = 2; i <= n; i++) {

fibonaccis[i] = UNCALCULATED;

} // end for

results = MemoizeFibonacci(n, fibonaccis);

delete [] fibonaccis;

return results;

} // end CalculateFibonacci