Question 1

Grading

One point per part. I gave 0.2 points as partial credit for the following incorrect answers: "Same" for Part 1. "B is faster" for Part 5. "Same" for Part 7.

How Y'all Did

A B =
Part 1 5 3 17
Part 2 19 4 2
Part 3 3 6 16
Part 4 21 1 3
Part 5 1 9 13
Part 6 17 6 1
Part 7 15 6 4
Part 8 12 7 6
Part 9 6 14 5
Part A 11 12 2
Part B 5 7 13
Part C 15 7 3
Part D 4 10 11
Part E 4 15 5
Part F 8 15 2


Question 2

The answer is ADBGHEFCI. Here are the steps:

Grading

Four points -- I did give partial credit.


Question 3

For Prim's algorithm, the answer is AD, DG, GH, HF, GE, FI, FC, CB. Prim's algorithm is a lot like Dijkstra's algorithm -- here are the states at each step:

For Kruskal's algorithm, you first sort the edges, then use Union find to add edges to the MST. If the edges connect nodes in different sets, then you add the edge to the tree and perform Union on the two nodes' sets. Here are the states. The answer was a slow-pitch -- the first 8 edges in their sorted order: AD, GH, HF, GE, FI, BC, CF, DG.

Grading

Four points each -- I did give partial credit.


Question 4

This is a simple BFS which uses a queue:

int Graph::Shortest_Path(Node *a, Node *b)
{
  int i;
  list <Node *> bfsq;
  list <Node *>::iterator bit;
  Node *n;

  for (i = 0; i < nodes.size(); i++) nodes[i]->tmp = -1;
  a->tmp = 0;
  bfsq.push_back(a);

  while (!bfsq.empty()) {
    bit = bfsq.begin();
    n = *bit;
    bfsq.erase(bit);
    if (n == b) return n->tmp;
    for (i = 0; i < n->edges.size(); i++) {
      if (n->edges[i]->tmp == -1) {
        n->edges[i]->tmp = n->tmp+1;
        bfsq.push_back(n->edges[i]);
      }
    }
  }
  return -1;
}

To test this, I hacked up a little main() which first creates a ten-node graph where node i has an edge to node i+1. It then prints out the path distance from node 0 to node 9 (which should be 9) and the path from node 9 to node 0 (which should be -1).

Then, for each node i I add edges to every node j such that j < i, and print out the same path lengths. Node 0 to node 9 should still have a path length of 9. Node 9 to node 0 should have a path length of 1. The code is in bfs.cpp

main()
{
  Graph g;
  Node *n;
  int i, j;

  for (i = 0; i < 10; i++) {
    n = new Node;
    g.nodes.push_back(n);
  }

  for (i = 0; i < 9; i++) {
    g.nodes[i]->edges.push_back(g.nodes[i+1]);
  }

  cout << g.Shortest_Path(g.nodes[0], g.nodes[9]) << endl;
  cout << g.Shortest_Path(g.nodes[9], g.nodes[0]) << endl;

  for (i = 0; i < 10; i++) {
    for (j = 0; j < i; j++) {
      g.nodes[i]->edges.push_back(g.nodes[j]);
    }
  }

  cout << g.Shortest_Path(g.nodes[0], g.nodes[9]) << endl;
  cout << g.Shortest_Path(g.nodes[9], g.nodes[0]) << endl;
}

UNIX> bfs
9
-1
9
1
UNIX> 

Grading

Basically, you started at a certain maximum value, depending on how you structured your code. These values were: After that, there were the following deductions:


Question 5

Re-read the lecture notes if you don't understand any of these answers.

Grading

One point for each of the 11 parts. I gave credit for the proper residual graph for your answer, even if your answer was wrong.


Question 6

The recursive definition maps directly to a recursive function. Simply use a cache to memoize it (This is in q4.cpp):

double CalcX::X(int x, int y)
{
  int i;
  double retval, tmp;

  // Set up the cache if need be.

  if (cache.size() < x+1) {
    cache.resize(x+1);
    for (i = 0; i <= x; i++) {
      if (cache[i].size() < y+1) cache[i].resize(y+1, -1);
    }
  }

  // Return the value from the cache if it is there.

  if (cache[x][y] != -1) return cache[x][y];

  // Otherwise, do the recursive calculation

  retval = 0;
  if (x == 0 && y == 0) retval = 1;
  if (x > 0) {
    tmp = F1(x-1, y);
    if (tmp > retval) retval = tmp;
  }
  if (y > 0) {
    tmp = F2(x, y-1);
    if (tmp > retval) retval = tmp;
  }

  // Put it into the cache and return

  cache[x][y] = retval;
  return retval;
}

Grading

As with Question 4, you started at a certain maximum value, depending on how you structured your code. These values were: After that, there were the following deductions: