Keyboard shortcuts

Press ← or → to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

The working column

Whatever the algorithm, reducing a column means repeating two operations on a working column \(R_i = D V_i\):

  • pop the pivot: find its largest entry (summing entries with the same row, and moving on when they cancel);
  • add a column: add a multiple of a column of \(D\) (or a stored column of \(R\)) to it.
flowchart LR
    W["working column R_i"] -->|pop pivot r| O{"r owned by<br/>column j?"}
    O -- no --> DONE["R_i owns r: done"]
    O -- yes --> ADD["add (a multiple of) R_j<br/>= add columns of D"]
    ADD --> W

How the working column is stored is its representation, a type implementing ColumnRepresentation, chosen with with_columns on any algorithm:

Clearing::new().with_columns(PivotColumns)

Every representation gives the same pairs; only the time and memory differ. The difference can be large: on some inputs the best is 30× faster than the worst. There are four:

RepresentationIdeaAnalogue
HeapColumnsevery term on one heapRipser
MergedColumns (default)lazily merge sorted columns, one heap slot per column
SortedColumnsone sorted vector, batches merged inPHAT’s vector_vector
PivotColumnsa dense array over all rows, plus a bit treePHAT’s bit_tree_pivot_column

Separately, a column cache can keep the columns of \(D\) that get added, sorted, so they are neither recomputed nor re-sorted. Choosing summarises when each wins.