August 21, 2023

Today

  • Wrap up parallelization
  • Dynamic programming

Multi-threading

  • Multiple threads completing tasks at the same time in the same memory space.

  • Pros:

    1. Easy and lightweight set-up.
    2. Don’t have to pass information across threads.
  • Cons:

    1. Need to worry about data races and over-writing shared memory conditions.
    2. Constrained by resources available on one computer/server.

Multi-processing

  • Multiple processors are completing tasks at the same time.

  • Each processor has its own memory space

  • Cons:

    1. Uses more memory because each cores has its own memory.
    2. Have to share info across cores when needed.
  • Pros:

    1. Don’t have to worry about data races.
    2. It is possible to work across multiple computers/servers.

Advice

  • Try to do multi-threading first.

  • When to do multi-processing:

    1. Having trouble avoiding data races and over-writing shared memory.
    2. Need more cores than are available on one slurm server.

Dynamic Programming Intro

  • Optimization problems in our economic models are often complicated.
    • Many states variables.
    • Many possible choices at each state.
    • Future decisions depend on previous decisions.
    • Agents are forward looking and care about future pay-offs.
  • Large number of calculations are necessary to find optimal decision rules.
  • We want to find solve these problems as quickly as possible.

Dynamic Programming

  • Dynamic programming simplifies the problem by:
    1. Breaking it down into smaller sub-problems
    2. Solve these sub-problems recursively.
  • Example: Suppose you want to make saving decision from age 25 to 65:
    • You could search over all possible savings paths. OR:
    1. First solve for optimal savings rule at age 65.
    2. Then given age 65 savings rules, solve for age 64 savings rule …
    3. Giving all future savings rules, solve for age 25 savings rule.

Dynamic Programming

  • The general idea:
    1. Break down the problem into smaller sub-problems.
    2. Start by solving the easiest of the sub-problems.
    3. Store results, which you will use to solve more sub-problems.
  • This is often much faster than just searching over all possible decisions.
  • Many problems would be computationally infeasible without dynamic programming.
  • Today we will go through some classic dynamic programming problems.

Fibonacci Sequence

  • Each number is the sum of the last two numbers: \[ F(n) = F(n-1) + F(n-2) \]
  • The Fibonacci sequence: \[ 0, 1, 1, 2, 3, 5, 8, 13, 21, ... \]
  • Saving results of previous sub-problem can speed up code dramatically.

Egg Dropping Problem

  • We have n eggs and there are k floors in a building.
  • We want to know the highest possible from which we can drop the egg without it breaking.
  • Want to do this as quickly as possible, so minimize the number of times we drop an egg.
  • Rules:
    • Eggs that survive can be used again, but broken eggs are discarded.
    • If an egg breaks on a floor, it would break on all higher floors.
    • If an egg doesn’t break on a floor, it wouldn’t break on all lower floors.
  • Let E(n,k) be the answer to the problem.

Solution

  • Suppose we have 1 egg and k floors.
    • We have to drop from every floor from the bottom.
    • E(1,k) = k
  • Suppose we have 2 eggs and k floors.
    • If we drop at floor j, either,
      • The egg breaks. We have 1 egg for j-1 floors.
      • The egg survives. We have 2 eggs to search k-j floors. \[ E(2,k) = \min_j\left\{\max \left\{E(1,j-1), E(2,k-j)\right\}\right\} \]
  • General formula is then:\(E(n,k) = \min_j\left\{\max \left\{E(n-1,j-1), E(n,k-j)\right\}\right\}\).

Shortest Travel Time

  • Suppose we are interested in the shortest travel time between a source city \(C_1\) and and some other cities \(\{C_j\}\).
  • Direct route is not always the fastest because of traffic and terrain.
  • The direct road distance between cities \(x,y\) is given by: \[ d(x,y). \]
  • If direct road doesn’t exist, say \(d(x,y) = \infty\).
  • We could check all possible routes from \(C_1\) to \(C_j\) for all \(j\), but that would take a while.

Dijkstra’s Algorithm

  • Start at source city \(C_1\). Calculate direct distance to all cities: \[ M(1,j) = d(C_1,C_j) \]
  • Second, visit the city with shortest distance to \(C_1\) that is not the source city. Call it \(C_v\). \[ C_{v} = \arg\min_j M(1,j) \]
  • Update distance for all cities \(j\) if it is faster to go through \(C_v\). \[ M(2,j) = \min\{M(1,j), M(1,v) + d(v,j)\} \]

Dijkstra’s Algorithm Continued

  • Next, go to the unvisited city with shortest distance to \(C_1\) that is not the source city or a previously visited city. \[ C_v = \arg\min M(2,j) \]
  • Again update distances if it is faster to travel through \(C_v\) first. If not, go previously found way.

  • Eventually, we arrive at minimum travel distance to all the the cities \[ M(N,j) = \min\{M(N-1,j), M(N-1,v) + d(v,j)\} \]