Scanning a serialized Data value #
Data.toBits writes a value as balanced brackets: false opens a node, its
children follow in order, and true closes it. Reading one child back out of
such a string is a single left-to-right pass keeping a bracket depth and a count
of the children already passed, collecting bits only while inside the child
asked for.
This module writes that pass in the form recFoldClamp accepts, so that
polynomial-time computability comes from the general fold rather than from a
bespoke machine. The fold recurses head-then-tail, so it runs right to left; the
caller therefore hands it the reversed string.
The state is pair (unary depth) (pair (unary count) collected) and the
workspace is the requested index in unary. Every component stays below the
length of the string being scanned, so a linear clamp suffices.
Main definitions #
Complexity.DataScan.openStep,closeStep— the two fold stepsComplexity.DataScan.childOf— the scan, packaged as one function
Main results #
Complexity.DataScan.childOf_mem_FP— the scan is polynomial timeComplexity.DataScan.recFoldClamp_eq_pack— the fold runs the modelComplexity.DataScan.child_flatten— the packaged scan extracts the childComplexity.DataScan.childCount_flatten— and counts the childrenComplexity.DataScan.inner_toBits— the bits between the outer brackets
Reading the packed fold argument #
recFoldClamp hands each step pair (pair W st) t, with W the workspace, st
the state built so far and t the unscanned tail.
The workspace: the index of the child being extracted, in unary.
Equations
Instances For
The state carried by the scan.
Equations
Instances For
The bracket depth, in unary.
Equations
Instances For
The number of children already passed, in unary.
Equations
Instances For
The bits collected so far.
Equations
Instances For
The two steps #
An opening bracket: descend one level.
Equations
Instances For
The state a scan starts from.
Equations
Instances For
Polynomial time #
The scan. On pair (unary i) s it runs the two steps over s, keeping
every intermediate state within p.eval bits, and returns the collected bits.
Equations
- One or more equations did not get rendered due to their size.
Instances For
The fold runs the model #
The state the fold carries is the model's state written out: two unary counters and the collected bits. Once that is checked step by step, the fold and the model agree, provided the clamp is wide enough never to truncate.
The model's state, written out as a bitstring.
Equations
- Complexity.DataScan.pack st = Complexity.pair (List.replicate st.1 true) (Complexity.pair (List.replicate st.2.1 true) st.2.2)
Instances For
The state stays small #
The packaged scan #
A clamp wide enough for any scan: the state never exceeds 5 n + 4 bits.
Equations
Instances For
The scan's argument: the index in unary paired with the reversed string, the order the fold consumes.
Equations
Instances For
The scan extracts the child. Reading the concatenated serializations of
xs returns the i-th one, or nothing when there is no such child.
How many children there are, in unary: the same pass, reading off the counter instead of the collected bits.
Equations
- One or more equations did not get rendered due to their size.