Documentation

DescriptiveComplexity.Problems.Wide.BlkFile

The file a clocked program lays out #

A space-bounded program gives every element of its universe a register (DescriptiveComplexity.segFile), and laying that file out costs one sweep of it. A program on a clock cannot pay that: a rule sees the control and the cell under the head and nothing else, so the only stretches it can walk are a fixed number of tuple roll-overs long, and the universe is |Tag| of those with |Tag| the program's own rule count.

What it can afford is one register per block and tuple, which is also all that a register's contents ever depend on: the block one-hot goes through DescriptiveComplexity.Draw.tagBlk alone and the name slots are the tuple, so nothing of a tag beyond its block is ever read back (DescriptiveComplexity.Draw.Data.ixBack). This file is that file: DescriptiveComplexity.blkFile, one register per DescriptiveComplexity.Wide.BlkIx, laid out on a stretch of consecutive addresses in the block-major order DescriptiveComplexity.Wide.blkLe.

Everything it needs is already general – the interface (DescriptiveComplexity.IxFile), the walks over it, the construction on a stretch (DescriptiveComplexity.ixSegFile) and the background (DescriptiveComplexity.Draw.Data.ixBack) – so all that is added here is the instantiation and the two numbers a caller has to check: how many registers there are, and that the stretch fits.

noncomputable def DescriptiveComplexity.blkFile (A K : Type) [LinearOrder A] [Finite A] [LinearOrder K] [Finite K] (U : Type) [FirstOrder.Language.wide.Structure U] [Finite U] (dd : ℕ) (h : IsLinOrd WMLe) {base : ℕ} (hpos : 0 < base) (hbase : base + Nat.card (Wide.BlkIx K A dd) ≤ Nat.card { p : WPoint U // (wideData U).Posn p }) :
IxFile U (Wide.BlkIx K A dd) (Wide.blkLe K A dd)

The file a clocked program lays out: one register per block and tuple, on the stretch of consecutive addresses whose ranks start at base.

Equations
Instances For
    Dependency graph
    theorem DescriptiveComplexity.card_blkFile {A K : Type} [Finite K] (dd : ℕ) :
    Nat.card (Wide.BlkIx K A dd) = (Nat.card K + 1) * Nat.card (Fin dd → A)

    How many registers the file has: one per block, one more for the blockless ones, times the tuples. This is the number the stretch has to fit, and the number of tuple roll-overs the laying sweep runs for.

    Dependency graph

    Walking the file: the pointer's advance and its two ends #

    The sweep that lays the file out carries the register it is at in the machine's control, and a rule advances it: dstSt is a function of the control, so the next register has to be a function of the current one, not merely to exist. These three are that function and the two ends its walk runs between; nothing here is computed – a rule's fields are semantic – so the choice off DescriptiveComplexity.exists_ixSucc is the definition, and its characterization is what a caller discharges the walk with.

    noncomputable def DescriptiveComplexity.blkNext (A K : Type) [LinearOrder A] [Finite A] [LinearOrder K] [Finite K] (dd : ℕ) (u : Wide.BlkIx K A dd) :
    Wide.BlkIx K A dd

    The next register: the successor of an index in the layout order, and the index itself at the top of it.

    Equations
    • One or more equations did not get rendered due to their size.
    Instances For
      Dependency graph
      noncomputable def DescriptiveComplexity.blkBot (A K : Type) [LinearOrder A] [Finite A] [LinearOrder K] [Finite K] (dd : ℕ) [Nonempty A] :
      Wide.BlkIx K A dd

      The first register: least in the layout order, where the laying sweep's pointer starts.

      Equations
      Instances For
        Dependency graph
        noncomputable def DescriptiveComplexity.blkTop (A K : Type) [LinearOrder A] [Finite A] [LinearOrder K] [Finite K] (dd : ℕ) [Nonempty A] :
        Wide.BlkIx K A dd

        The last register: greatest in the layout order, where it stops.

        Equations
        Instances For
          Dependency graph
          noncomputable def DescriptiveComplexity.tupTop (A : Type) [LinearOrder A] [Finite A] (dd : ℕ) [Nonempty A] :
          Fin dd → A

          The last tuple: greatest in the tuples' own lexicographic order. A pointer holding it is at the last register of its block, which is what a roll-over's guard reads.

          Equations
          Instances For
            Dependency graph
            noncomputable def DescriptiveComplexity.blkNextB (A K : Type) [LinearOrder A] [Finite A] [LinearOrder K] [Finite K] (dd : ℕ) [Nonempty A] (b : Option K) :

            The next block: the block of the register after the last of this one. A destination phase is a constant, so a roll-over rule needs the next block as a function of the current one alone, and this is it.

            Equations
            Instances For
              Dependency graph

              The stretch fits #

              The one arithmetic fact a caller of DescriptiveComplexity.blkFile owes: the file has fewer registers than the universe has elements – a block and a tuple is an element of the universe, the blockless register taking the alphabet tag – and the addresses are 2 ^ that, so a stretch based at 1 always fits.

              The blockless register and each block, as tags: the alphabet tag stands for the blockless one.

              Equations
              Instances For
                Dependency graph
                Dependency graph

                The address a clocked file's marks stand for #

                A mark on the file is an address of the tape (DescriptiveComplexity.ixAddr), and the correspondence is what lets a program hold an address it cannot see – the one under its head – on registers it can. It is only used on the argument registers, and the two conditions of DescriptiveComplexity.wmIncr_ixAddr hold of exactly those: the argument tags are the greatest ones (DescriptiveComplexity.Draw.lt_arg), so nothing the file has no register for lies above an argument element, and the block order was chosen to make DescriptiveComplexity.blkTag monotone.

                def DescriptiveComplexity.blkIxElt {A : Type} (R P : Type) {K : Type} (dd : ℕ) (u : Wide.BlkIx K A dd) :
                Draw.Univ A R P K dd

                The element a register holds the bit of.

                Equations
                Instances For
                  Dependency graph
                  def DescriptiveComplexity.BlkIxUse (A K : Type) (dd : ℕ) (u : Wide.BlkIx K A dd) :

                  The registers an address uses: the argument blocks, the blockless ones standing for the alphabet tag and never entering a logical address.

                  Equations
                  Instances For
                    Dependency graph
                    theorem DescriptiveComplexity.blkIxElt_mono {A R P K : Type} [LinearOrder A] [LinearOrder R] [LinearOrder P] [LinearOrder K] (dd : ℕ) [FirstOrder.Language.wide.Structure (Draw.Univ A R P K dd)] (hord : ∀ (x y : Draw.Univ A R P K dd), WMLe x y ↔ tagTupleLe x y) (u u' : Wide.BlkIx K A dd) :
                    WMLt (Wide.blkLe K A dd) u u' ↔ WMLt WMLe (blkIxElt R P dd u) (blkIxElt R P dd u')

                    The register order is the element order, strictly.

                    Dependency graph
                    theorem DescriptiveComplexity.blkIxElt_up {A R P K : Type} [LinearOrder A] [LinearOrder R] [LinearOrder P] [LinearOrder K] (dd : ℕ) [FirstOrder.Language.wide.Structure (Draw.Univ A R P K dd)] (hord : ∀ (x y : Draw.Univ A R P K dd), WMLe x y ↔ tagTupleLe x y) {u : Wide.BlkIx K A dd} (hu : BlkIxUse A K dd u) {x : Draw.Univ A R P K dd} (hlt : WMLt WMLe (blkIxElt R P dd u) x) :
                    ∃ (u' : Wide.BlkIx K A dd), BlkIxUse A K dd u' ∧ blkIxElt R P dd u' = x

                    Nothing without a register lies above an argument element: the argument tags come last, so the elements the file names are upward closed and the addresses over them are an initial interval of the tape.

                    Dependency graph