Clock constructibility for the time hierarchy theorem #
TM.ClockConstructible g is the constructibility hypothesis used by the
proved time hierarchy theorem in Complexitylib.Classes.Hierarchy: an
8-tape machine can write the unary clock regTape (g n) on work tape 6 in time
O(g n + n), ghost-preserving the rest of the diagonalizer's tape layout.
Contents:
TM.ClockConstructible— the layout-pinned definition (see its docstring for the design tradeoffs), plus the congruence helperClockConstructible.congr.TM.clockLenTMandTM.clockConstructible_succ— the base instanceClockConstructible (fun n => n + 1)via a single input sweep.TM.moveClockTM,TM.clockMulTMandClockConstructible.mul_succ— closure under multiplication byn + 1: move the clock to the scratch tape, then append it to the clock tape's frontier once per input position.TM.clockConstructible_pow—ClockConstructible (fun n => (n + 1) ^ k)for allk ≥ 1: the polynomial clocks of the hierarchy theorem.
All machines are hand-written in the UTM house style (small inductive
state, ghost-framed step/run lemmas as in UTM/Clock.lean and
InputLen.lean).
The canonical parked blank tape (liftTM's pinned extra tape) is the
zero register.
Clock constructibility — the hypothesis of the time hierarchy
theorem. g is clock-constructible if some 8-tape machine, started on
input x in the diagonalizer's tape layout, writes the unary register
regTape (g |x|) on work tape 6 within C * (g |x| + |x| + 1) steps,
disturbing nothing else.
The definition is deliberately layout-pinned rather than maximally
general: the diagonalizer D is an 8-tape machine whose UTM phases run
on tapes 0–5, whose encoded pair ⟨M, x⟩ lives on tape 7, and whose
clock lives on tape 6. Instead of a lift-and-frame story, the
hypothesis quantifies over the ghost frame work₀ directly:
- tapes 0–4 and 7 may hold arbitrary parked content (head ≥ 1,
reading a non-
▷symbol) and must be preserved exactly; - tape 6 (the clock) starts as the canonical parked blank tape
(Tape.init []).move Dir3.right(the tape theliftTMcombinators pin blank extras to; it equalsregTape 0) and ends asregTape (g |x|); - tape 5 is a designated scratch tape: it must also start blank,
and it is restored blank — this is exactly the
work i = work₀ iclause ati = 5, sincework₀ 5is pinned blank.Druns clock-initialization before any UTM phase touches tapes 0–5, so granting the clock machine one blank scratch tape costs nothing, and it makes the closure constructions (multiplication, hence all polynomials) feasible; - the input tape is read-only, so only its cells are pinned; its head
starts at cell 1 — the started form the combinator seams produce
(
transitionInputforces the input head to ≥ 1 at every phase boundary, so a head-0 input can never reach a mid-sequence phase) — and is returned to cell 1 (needed to chain clock phases sequentially); - the output tape must be
▷-clean with head parked at cell 1, and is returned in the same state (clock machines never write the output).
Equations
- One or more equations did not get rendered due to their size.
Instances For
ClockConstructible respects pointwise-equal clock bounds.
Measure the input length plus one into the clock tape: scan the
input left to right writing one mark on tape 6 per bit, write one
final mark at the input's first blank (the + 1), then rewind both
heads to cell 1 in lockstep. Every other tape idles throughout.
Equations
- One or more equations did not get rendered due to their size.
Instances For
The successor function is clock-constructible: clockLenTM writes
|x| + 1 clock marks in a single input sweep, well within the
2 * (g n + n + 1) budget.
Move the clock register to the scratch tape: sweep right over tape
6's marks, blanking each while writing a mark on tape 5 in lockstep,
then rewind both heads to cell 1. From (regTape 0, regTape v) on tapes
(5, 6) to (regTape v, regTape 0); every other tape idles throughout.
Equations
- One or more equations did not get rendered due to their size.
Instances For
Equations
- One or more equations did not get rendered due to their size.
Multiply the moved clock by |x| + 1: with regTape v on the scratch
tape 5 and an empty clock tape 6 (head at its frontier, cell 1), run one
round per scratch mark (drive consumes it): each round scans the input
left to right appending one clock mark per bit plus one at the first
blank (inScan), then rewinds the input head to cell 1 (inRew). The
clock head never leaves its frontier, so each round costs 2|x| + 3
steps. After the last round the scratch is blanked while rewinding
(rewC), the clock rewinds to cell 1 (rew6), and the machine parks:
tape 5 is regTape 0 and tape 6 is regTape (v * (|x| + 1)).
Equations
- One or more equations did not get rendered due to their size.
Instances For
Closure under multiplication by n + 1. Run the g-clock, move
its register to the scratch tape (moveClockTM), then append it to the
clock tape's frontier once per input position (clockMulTM), producing
regTape (g n * (n + 1)) in time O(g n * (n + 1) + n). This is where
the designated scratch tape 5 earns its keep.
Polynomial clocks: every positive power of n + 1 is
clock-constructible — the clock family the time hierarchy theorem uses
against polynomial time bounds.