ICS 582Lecture 02Part 11
Filling the DP table and recovering the alignment
The full algorithm, a cell by cell computation for intention to execution, backpointers and backtrace to read off the alignment, the time and space complexity, and the lecture in one page.
- Concepts
- 5
- Slides
- 87-94
- Reading
- 30 min
Why this part matters
The edit distance table is the most examinable algorithm in this lecture. SLP3 sets it as a by-hand exercise, and every spelling, transliteration or speech evaluation you will run in your research is this table applied to characters or words: word error rate is literally an edit distance divided by a length.
Part 10 defined the problem and the recurrence. This part makes the algorithm run. You will fill the 10 x 10 table for intention to execution cell by cell, see why the slide's table ends in 8 while the unit-cost answer is 5, store arrows as you go, and then walk those arrows home to read an alignment off the table. The same fill-then-backtrace pattern returns later in the course as Viterbi decoding and CKY parsing, so the effort pays three times.
By the end you can
- Initialize and fill an edit distance table by hand under a stated cost convention and read the distance from D[n,m].
- Store argmin arrows while filling and backtrace them into an alignment with operation letters.
- Explain what a tie in the argmin means for the number of optimal alignments.
- State time and space complexity, and how two rows or Hirschberg's recursion reduce space.
- Explain why slide 89 ends in 8 while unit costs give 5, and pass an exam under either convention.
Start with a route you can check by eye. Take intention, delete the i to get ntention, replace n by e to get etention, replace t by x to get exention, insert u to get exenution, and replace n by c to get execution. Five edits, each of cost 1, and the string arrives exactly where it should.
- intention, delete i, gives ntention
- ntention, substitute n by e, gives etention
- etention, substitute t by x, gives exention
- exention, insert u, gives exenution
- exenution, substitute n by c, gives execution
SLP3 states that the unit-cost Minimum edit distance between these two words is exactly 5, so this ladder is not merely a route, it is an optimal one. The interesting question is what optimality implies about the middle rungs. Suppose exention really lies on a shortest path. Then the way we reached exention must itself be the shortest way to reach exention: if a cheaper route to exention existed, we could splice it in and get a cheaper route to execution, which contradicts the assumption that our path was shortest. Every prefix of a shortest path is a shortest path. That property is called Optimal substructure, and it is the license for Dynamic programming: instead of remembering whole edit sequences, remember the best cost for every intermediate state once, and build longer answers out of shorter ones.
The states themselves are what part 10 introduced: a pair of prefixes, the first i letters of the source and the first j letters of the target. The naive search over edit sequences explodes because thousands of different sequences pass through the same intermediate string, and each one is scored again from scratch. A table indexed by prefix pairs collapses all of those into one cell, and the Alignment you read from the table at the end is just the ladder above, laid out as a path through cells (SLP3, section 2.9.1).
Recall
Why does the fact that exention lies on an optimal path from intention to execution tell you anything about the path from intention to exention?
Compute the top-left corner of the intention to execution table by hand, using the slide's convention where a substitution costs 2. The empty string needs nothing to become the empty string, so D[0,0] = 0. Turning the one-letter prefix i into nothing takes one deletion, D[1,0] = 1. Building e from nothing takes one insertion, D[0,1] = 1. The first interior cell compares i with e: D[1,1] = min(1 + 1, 1 + 1, 0 + 2) = 2, and all three candidates tie.
That small calculation is the whole algorithm, repeated. SLP3's pseudocode (its Fig. 2.21, reproduced on slide 88) makes it precise. Let n be the length of the source and m the length of the target, and create a matrix D with n + 1 rows and m + 1 columns, the extra row and column standing for the empty prefix. The first column is D[i,0] = D[i-1,0] + del-cost(source[i]), because the only way to turn a length-i prefix into nothing is to delete each of its letters. The first row is D[0,j] = D[0,j-1] + ins-cost(target[j]), because the only way to build a length-j prefix from nothing is to insert each letter. With unit insertion and deletion those two lines reduce to D[i,0] = i and D[0,j] = j. Then, row by row and column by column, every interior cell is the minimum of three candidates, and the answer is D[n,m].
The Edit distance recurrence looks only at three neighbors: the cell above (delete the source letter source[i], written x_i in the formula), the cell to the left (insert the target letter target[j], written y_j), and the diagonal cell (substitute one for the other, or match for free when they are equal). Nothing else in the two strings is consulted. That locality is what makes the fill order work: going row by row from the top-left, all three neighbors are already computed when you reach a cell. Any order with that property is fine, including column by column or along anti-diagonals, which is how the hover figure below animates it.
Two conventions, two right answers
Slide 86 defined a unit Substitution cost, but the table on slide 89 is SLP3's Fig. 2.20, which charges 2 for a substitution. SLP3 explains the choice: a substitution can always be simulated by one deletion and one insertion, so charging 2 makes the metric coincide with the version of Levenshtein's distance that allows only insertions and deletions. Under that convention intention to execution costs 8; under unit costs it is 5, the length of the ladder from the previous concept. Both numbers are correct in their own world, and an exam answer is correct only if it names the world it lives in.
| Convention | Insert | Delete | Substitute | Match | Distance | Optimal alignments |
|---|---|---|---|---|---|---|
| Unit (Levenshtein) | 1 | 1 | 1 | 0 | 5 | 7 |
| SLP3 table (slide 89) | 1 | 1 | 2 | 0 | 8 | 134 |
Here is the full table from the slide with the source intention down the rows and the target execution across the columns, followed by the same table under unit costs. Compare any substitution cell: D[1,1] is 2 in the first and 1 in the second, and that one-point gap propagates until the corners read 8 and 5.
| # | e | x | e | c | u | t | i | o | n | |
|---|---|---|---|---|---|---|---|---|---|---|
| # | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 |
| i | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 6 | 7 | 8 |
| n | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 7 | 8 | 7 |
| t | 3 | 4 | 5 | 6 | 7 | 8 | 7 | 8 | 9 | 8 |
| e | 4 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 9 |
| n | 5 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 10 |
| t | 6 | 5 | 6 | 7 | 8 | 9 | 8 | 9 | 10 | 11 |
| i | 7 | 6 | 7 | 8 | 9 | 10 | 9 | 8 | 9 | 10 |
| o | 8 | 7 | 8 | 9 | 10 | 11 | 10 | 9 | 8 | 9 |
| n | 9 | 8 | 9 | 10 | 11 | 12 | 11 | 10 | 9 | 8 |
| # | e | x | e | c | u | t | i | o | n | |
|---|---|---|---|---|---|---|---|---|---|---|
| # | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 |
| i | 1 | 1 | 2 | 3 | 4 | 5 | 6 | 6 | 7 | 8 |
| n | 2 | 2 | 2 | 3 | 4 | 5 | 6 | 7 | 7 | 7 |
| t | 3 | 3 | 3 | 3 | 4 | 5 | 5 | 6 | 7 | 8 |
| e | 4 | 3 | 4 | 3 | 4 | 5 | 6 | 6 | 7 | 8 |
| n | 5 | 4 | 4 | 4 | 4 | 5 | 6 | 7 | 7 | 7 |
| t | 6 | 5 | 5 | 5 | 5 | 5 | 5 | 6 | 7 | 8 |
| i | 7 | 6 | 6 | 6 | 6 | 6 | 6 | 5 | 6 | 7 |
| o | 8 | 7 | 7 | 7 | 7 | 7 | 7 | 6 | 5 | 6 |
| n | 9 | 8 | 8 | 8 | 8 | 8 | 8 | 7 | 6 | 5 |
Worked example
Three cells of the slide's table, substitution cost 2
D[1,1], i versus e
Up gives D[0,1] + 1 = 2, left gives D[1,0] + 1 = 2, diagonal gives D[0,0] + 2 = 2. All three tie, so D[1,1] = 2 and the cell stores three arrows.D[4,2], e versus x
Up gives D[3,2] + 1 = 6, left gives D[4,1] + 1 = 4, diagonal gives D[3,1] + 2 = 6. Left wins alone, so D[4,2] = 4 with a single left arrow.D[7,7], i versus i
The letters match, so the diagonal is free: D[6,6] + 0 = 8. Up and left would give 9 + 1 and 9 + 1, so D[7,7] = 8 with one diagonal arrow.Result
Continuing to the corner, D[9,9] = 8. Under unit costs the same three cells read 1, 4 and 5, and the corner reads 5.
Worked example
A table you can finish in a minute: cat to cut, unit costs
Borders
Row # is 0 1 2 3 and column # is 0 1 2 3.Row c
c matches c, so D[1,1] = 0; then D[1,2] = 1 and D[1,3] = 2 by inserting u and t.Row a
D[2,1] = 1 (delete a), D[2,2] = min(1 + 1, 0 + 1, 1 + 1) = 1 (substitute a by u), D[2,3] = 2.Row t
D[3,1] = 2, D[3,2] = 2, and t matches t so D[3,3] = D[2,2] + 0 = 1.Result
Distance 1, alignment c a t over c u t with one substitution.
| # | c | u | t | |
|---|---|---|---|---|
| # | 0 | 1 | 2 | 3 |
| c | 1 | 0 | 1 | 2 |
| a | 2 | 1 | 1 | 2 |
| t | 3 | 2 | 2 | 1 |
Now run the same procedure yourself. The simulator fills any pair of short words one cell at a time, prints the three candidates for each new cell, stores the arrows, and keeps both conventions side by side so you can watch the corner change from 5 to 8 with one toggle. The backtrace button belongs to the next concept; try it after reading on.
| # | e | x | e | c | u | t | i | o | n | |
|---|---|---|---|---|---|---|---|---|---|---|
| # | ||||||||||
| i | ||||||||||
| n | ||||||||||
| t | ||||||||||
| e | ||||||||||
| n | ||||||||||
| t | ||||||||||
| i | ||||||||||
| o | ||||||||||
| n |
D[0,0] = 0: the empty string is already the empty string.
| Convention | Substitution cost | Distance | Optimal alignments |
|---|---|---|---|
| Unit (Levenshtein) | 1 | 5 | 7 |
| SLP3 table (slide 89) (shown) | 2 | 8 | 134 |
Quick check
In the recurrence, which candidate corresponds to deleting the source letter source[i]?
Quick check
Slide 89 ends at 8 for intention to execution, but unit costs give 5. What explains the difference?
Recall
Why is the first column initialized to i and the first row to j?
Recall
Which three cells does D[i,j] depend on, and what operation does each represent?
Put your finger on the 8 in the bottom-right corner of slide 91. That cell holds a single diagonal arrow, because n matches n and the free diagonal was the only candidate that reached 8. Step diagonally to (8,8), still 8, o matches o. Diagonal again to (7,7) for i, and to (6,6) for t. At (5,5) three arrows are drawn; the bold path takes the diagonal, substituting n by u for 2, which is why the value drops from 8 to 6 at (4,4). That cell has only a left arrow: insert c. Then (4,3) matches e for free, (3,2) substitutes t by x, (2,1) substitutes n by e, and (1,0) points up, deleting i, into (0,0).
| Cell | Value | Arrow taken | Meaning |
|---|---|---|---|
| (9,9) | 8 | diagonal | n matches n, cost 0 |
| (8,8) | 8 | diagonal | o matches o, cost 0 |
| (7,7) | 8 | diagonal | i matches i, cost 0 |
| (6,6) | 8 | diagonal | t matches t, cost 0 |
| (5,5) | 8 | diagonal | n to u, cost 2 (one of three arrows) |
| (4,4) | 6 | left | insert c, cost 1 |
| (4,3) | 5 | diagonal | e matches e, cost 0 (one of two arrows) |
| (3,2) | 5 | diagonal | t to x, cost 2 (one of three arrows) |
| (2,1) | 3 | diagonal | n to e, cost 2 (one of three arrows) |
| (1,0) | 1 | up | delete i, cost 1 |
| (0,0) | 0 | stop | origin reached |
Reverse the list and you have an edit sequence: delete i, n to e, t to x, match e, insert c, n to u, then four matches. Its cost is 1 + 2 + 2 + 0 + 1 + 2 + 0 + 0 + 0 + 0 = 8, the corner value, and written as rows it is SLP3's Fig. 2.17: INTE*NTION over *EXECUTION with the operation letters d s s i s under the changed columns. This is a different five-edit shape from the ladder in the first concept, yet it costs the same under both conventions, 8 here and 5 at unit costs: the ladder substitutes n by c and then inserts u, the bold path inserts c and then substitutes n by u, and both keep the four free matches at the end. The two diverge exactly at the three-arrow tie in (5,5): the left arrow leads to the ladder, the diagonal to the bold path. That is the tie rule of the next subsection in action.
The general mechanism is what slide 90 states. While filling, each cell records which of its three candidates achieved the minimum, the argmin, as a Backpointer. Up means the source letter was deleted, left means the target letter was inserted, diagonal means substitution or match. After the fill, start at D[n,m] and follow arrows until D[0,0]. SLP3 puts it in one sentence: each complete path between the final cell and the initial cell is a minimum distance Alignment. Every step decreases i, j or both, so the walk takes at most n + m steps, which is why SLP3's lecture slides list the Backtrace as O(n + m).
How to read an arrow
- Up
- delete source[i], move to (i-1, j); two bold cells in one column
- Left
- insert target[j], move to (i, j-1); two bold cells in one row
- Diagonal
- substitute or match, move to (i-1, j-1); cost 0 when the letters are equal
Ties are alternative alignments
A cell like (1,1) on slide 91 carries three arrows because three candidates reached the same minimum. SLP3 says this directly: some cells have multiple backpointers because the minimum extension could have come from multiple previous cells. Each choice at a tie leads to a different complete path, and every complete path has the same total cost, so ties are exactly the reason multiple optimal alignments exist. For intention to execution there are 134 such paths under the cost-2 convention and 7 under unit costs (both counted for this part by walking every pointer set). Erickson shows a smaller case in his textbook, ALGORITHM to ALTRUISTIC, whose table has exactly three optimal paths. Go back to the simulator, press Backtrace, then Next alignment, and watch the highlighted path change at the teal-dotted cells while the distance stays fixed.
Quick check
A backpointer cell carries three arrows. What does that tell you about the alignments?
Recall
A cell has two arrows. What does this mean for the alignments?
Recall
Fill the unit-cost table for cat to cut and give the distance and one alignment.
The intention to execution table has 10 x 10 = 100 cells, and each cost a glance at three neighbors. Two documents of 100,000 characters each would need 10^10 cells, which is the scale where the accounting starts to matter and where the Stanford CS 262 notes on alignment begin their discussion of space.
Time is the easy half. There are (n + 1)(m + 1) cells, each computed in constant time from three already-known neighbors, so the fill runs in O(mn), the bound Wagner and Fischer gave in 1974 and the one Erickson states for his edit distance chapter. Space is where the choices begin. Storing the whole table, as the simulator does, also takes O(mn). But look at the recurrence again: row i reads only row i - 1 and the cells to its own left. If all you want is the distance, keep two rows, the previous one and the one being filled, and throw the rest away. Put the shorter string across the columns and the memory is O(min(m,n)), exactly what slide 92 says.
The price of that saving is the third bullet of the slide. The backpointers lived in the rows you discarded, so the two-row version cannot Backtrace. Erickson puts it plainly: by throwing away most of the table, we apparently lose the ability to walk backward. If you need the alignment as well, either keep the full table with its arrows, or recompute cleverly. Hirschberg's 1975 algorithm is the clever recomputation: run the two-row fill forward from the start and backward from the end, meet in the middle column to find which cell of that column the optimal path passes through, then recurse on the two halves. It recovers the full alignment in O(m + n) space while staying O(mn) in time; the CS 262 proof shows the constant roughly doubles, because every level of the recursion refills about half the area of the level above.
| Goal | Time | Space | What to store |
|---|---|---|---|
| Distance only | O(mn) | O(min(m,n)) | Two rows: the previous one and the one being filled |
| Distance and alignment | O(mn) | O(mn) | The whole table with an arrow set in every cell |
| Alignment in linear space | O(mn), about twice the constant | O(m+n) | Hirschberg's divide-and-conquer recursion, no stored table |
Quick check
You need only the distance between two strings of lengths m and n. What is the least memory the standard algorithm needs?
Recall
You need only the distance between two long strings. How much memory do you need and why?
Slide 93 closes the lecture with seven lines, and they tell one story. A word is not a universal primitive, so Tokenization is a design decision rather than a fact about text. Whatever units you pick, their frequencies follow a heavy tail (Zipf for rank against frequency, Heaps for vocabulary growth), so a fixed word vocabulary always leaks unseen words, and subwords are the answer.
Morphology shows that words do have meaningful pieces, morphemes, but that segmenting them cleanly is hard and differs across languages. Unicode and UTF-8 make multilingual text representable at all, and their bytes are the universal fallback when nothing else fits. BPE then learns a compact, reusable subword vocabulary from data, with a regex pre-tokenizer doing the practical work of splitting and normalizing before it. Finally, once text has become strings of units, the Minimum edit distance table you just filled is the foundational dynamic program for saying how similar two of those strings are.
- Word is not a universal primitive; tokenization is a design decision.
- Vocabulary growth follows a heavy tail (Zipf, Heaps), which motivates subwords.
- Morphology differs across languages; morphemes are meaningful but not always easy to segment.
- Unicode and UTF-8 make multilingual text possible, and bytes are a universal fallback.
- BPE learns a compact, reusable subword vocabulary.
- Regex is the practical tool for pre-tokenization and normalization.
- Minimum edit distance is the foundational DP algorithm for string similarity.
Recap
If you remember nothing else
- D[i,0] = i deletions, D[0,j] = j insertions, D[0,0] = 0.
- D[i,j] is the minimum of up plus delete, left plus insert, and diagonal plus substitute, where substitute costs 0 on a match.
- intention to execution costs 5 under unit costs and 8 under SLP3's cost-2 substitution; slide 89 uses cost 2.
- Store the argmin arrows while filling; backtrace from D[n,m] to D[0,0] in O(n+m) steps; several arrows in a cell mean several optimal alignments (134 at cost 2, 7 at cost 1 for this pair).
- Time O(mn). Space O(mn) with the table, O(min(m,n)) with two rows when only the distance is needed. Hirschberg recovers the alignment in O(m+n) space.
- Lecture takeaways: tokenization is a design decision; heavy tails motivate subwords; morphemes are meaningful but hard to segment; Unicode and UTF-8 with bytes as the fallback; BPE learns a compact vocabulary; regex handles pre-tokenization and normalization; edit distance is the foundational DP for string similarity.
Sources
- Speech and Language Processing, 3rd edition, chapter 2: Words and TokensBookStanford University (Jurafsky and Martin)Section 2.9, Eq. 2.19 and 2.20, Figs. 2.17 and 2.19 to 2.22 in the August 19, 2026 release(opens in a new tab)
- Speech and Language Processing, online manuscript indexDocsStanford University (Jurafsky and Martin)Cited on slide 94 as the January 6, 2026 manuscript(opens in a new tab)
- Minimum Edit Distance lecture slidesDocsStanford University (Jurafsky)Time O(nm), space O(nm), backtrace O(n+m); remember where you came from(opens in a new tab)
- The String-to-String Correction ProblemPaperJournal of the ACM 21(1):168-173, 1974 (Wagner and Fischer)The O(mn) dynamic programming algorithm(opens in a new tab)
- A linear space algorithm for computing maximal common subsequencesPaperCommunications of the ACM 18(6):341-343, 1975 (Hirschberg)Alignment recovery in O(mn) time and linear space(opens in a new tab)
- Binary codes capable of correcting deletions, insertions, and reversalsPaperDoklady Akademii Nauk SSSR 163(4):845-848, 1965 (Levenshtein)Origin of the Levenshtein distance(opens in a new tab)
- Algorithms, chapter 3: Dynamic ProgrammingBookJeff Erickson, University of IllinoisEdit distance in O(mn) time and space; ALGORITHM to ALTRUISTIC with three optimal paths(opens in a new tab)
- Algorithms, appendix D: Advanced Dynamic Programming, D.1 Saving SpaceBookJeff Erickson, University of IllinoisTwo-row trick, loss of the backward walk, and Hirschberg's O(m+n) space bound(opens in a new tab)
- CS 262 lecture 3 notes: Linear Space AlignmentDocsStanford UniversityTwo-column scoring, Hirschberg's O(N+M) space and O(MN) time with about twice the constant(opens in a new tab)
- Introduction to Algorithms, 4th editionBookMIT Press, 2022 (Cormen, Leiserson, Rivest and Stein)Dynamic programming chapter: optimal substructure and overlapping subproblems(opens in a new tab)