on bdf9204 help sign in
urbit.org/docs/hoon/basic.md
167 lines 6.6 kB history raw
1---
2navhome: '/docs/'
3next: True
4sort: 15
5title: Basic types
6---
8# Basic types
10A `span` is a set of nouns and an interpretation of these nouns. Officially, we
11don't use the word "type" in Hoon. But if we had to say "type," it would mean
12`span`.
14## Type, span and mold
16There is no Hoon syntax for a span. The programmer never defines a span
17explicitly. It is always produced as the inferred range of an expression
18(`twig`).
20But we still need simple, well-formed expressions that produce regular and
21well-shaped ranges, for three reasons.
23First: in most cases, this trivial generator should be much simpler than the
24computation itself. Casting the actual result to its ideal shape makes sure we
25know what we're building.
27Second: we can define a standard form for such generators, and the standard form
28is useful. The standard form is a constructor function, or *mold*.
30A mold is an idempotent function (`gate`), accepting any noun. (An idempotent
31function is one such that *f(f(x))* equals *f(x)* if *f(x)* terminates.) The
32product range of the function is the span, or *icon*, of the mold.
34Usually we use molds purely in the first sense: as an abstract definition of a
35noun. Don't actually call a mold unless you're actually validating untrusted
36foreign data. As a beginner, hopefully you aren't!
38## `span`: a set of nouns
40Below is the mold for `span`. You haven't seen this syntax before, and we
41haven't explained it yet; just treat it as pseudocode.
43This is a slightly simplified version of `span`. We undo and explain the
44simplifications in the [advanced types](../advanced) section.
46 ++ term @tas
47 ++ span
48 $@ $? $noun
49 $void
50 == $% {$atom p/term q/(unit atom)}
51 {$cell p/span q/span}
52 {$core p/span q/(map term twig)}
53 {$face p/term q/span}
54 {$fork p/(set span)}
55 {$hold p/span q/twig}
56 ==
58If a span is an atom, it's either the atomic string `noun` or `void`; if a cell,
59it's a tuple with one of the heads `atom`, `cell`, `core`, etc. We'll go through
60each of these cases below.
62### `?($noun $void)`
64`$noun` is the set of all nouns. `$void` is the set of no nouns.
66### `{$cell p/span q/span}`
68`{$cell p/span q/span}` is the set of all cells with head `p` and tail `q`.
70### `{$fork p/(set span)}`
72`{$fork p/(set span)}` is the union of all spans in the set `p`.
74### `{$hold p/span q/twig}`
76A `$hold` span, with span `p` and twig `q`, is a lazy reference to the span of
77`(mint p q)`. In English, it means: "the type of the product when we compile `q`
78against subject `p`."
80### `{$face p/term q/span}`
82A `{$face p/term q/span}` wraps the label `p` around the span `q`. `p` is a
83`term` or `@tas`, an atomic ASCII string which obeys symbol rules: lowercase and
84digit only, infix hyphen, first character must be lowercase.
86See [`:limb`](../twig/limb/limb) for how labels are resolved. It's nontrivial.
88### `{%atom p/term q/(unit atom))}`
90An `$atom` is an atom, with two twists. `q` is a `unit`, Hoon's equivalent of a
91nullable pointer or a Haskell `Maybe`. If `q` is `~`, null, the span is *warm*;
92any atom is in the span.\
93If `q` is `[~ x]`, where `x` is any atom, the span is *cold*; its only legal
94value is the constant `x`.
96`p` in the atom is a terminal used as an *aura*, or soft atom type. Auras are a
97lightweight, advisory representation of the units, semantics, and/or syntax of
98an atom. An aura is an atomic string; two auras are compatible if one is a
99prefix of the other.
101For instance, `@t` means UTF-8 text (LSB low), `@ta` means ASCII text, and
102`@tas` means an ASCII symbol. `@u` means an unsigned integer, `@ud` an unsigned
103decimal, `@ux` an unsigned hexadecimal. You can use a `@ud` atom as a `@u` or
104vice versa, but not as a `@tas`.
106Auras can also end with an optional, capitalized suffix, which defines the
107atom's bitwidth as a log starting from `A`. For example, `@udD` is an unsigned
108decimal byte; `@uxG` is an unsigned 64-bit hexadecimal.
110You can make up your own auras and are encouraged to do so, but here are some
111conventions bound to constant syntax:
113 @c UTF-32 codepoint
114 @d date
115 @da absolute date
116 @dr relative date (ie, timespan)
117 @f yes or no (inverse boolean)
118 @n nil
119 @p phonemic base (plot)
120 @r IEEE floating-point
121 @rd double precision (64 bits)
122 @rh half precision (16 bits)
123 @rq quad precision (128 bits)
124 @rs single precision (32 bits)
125 @s signed integer, sign bit low
126 @sb signed binary
127 @sd signed decimal
128 @sv signed base32
129 @sw signed base64
130 @sx signed hexadecimal
131 @t UTF-8 text (cord)
132 @ta ASCII text (span)
133 @tas ASCII symbol (term)
134 @u unsigned integer
135 @ub unsigned binary
136 @ud unsigned decimal
137 @uv unsigned base32
138 @uw unsigned base64
139 @ux unsigned hexadecimal
141Auras are truly soft; you can turn any aura into any other, statically, by
142casting through the empty aura `@`. Hoon is not dependently typed and can't
143statically enforce data constraints (for example, it can't enforce that a `@tas`
144is really a symbol).
146### `{$core p/span q/(map term span)}`
148A `$core` is a code-data cell. The data (or *payload*) is the tail; the code (or
149*battery*) is the head. `p`, a span, is the span of the payload. `q`, a
150name-twig table, is the source code for the battery.
152Each twig in the battery source is compiled to a formula, with the core itself
153as the subject. The battery is a tree of these formulas, or *arms*. An arm is a
154computed attribute against its core.
156All code-data structures in normal languages (functions, objects, modules, etc)
157become cores in Hoon. A Hoon battery looks a bit like a method table, but not
158every arm is a "method" in the OO sense. An arm is a computed attribute. A
159method is an arm whose product is a Hoon function (or *gate*).
161A gate (function, lambda, etc) is a core with one arm, whose name is the empty
162symbol `$`, and a payload whose shape is `{sample context}`. The *context* is
163the subject in which the gate was defined; the *sample* is the argument.
165To call this function on an argument `x`, replace the sample (at tree address
166`6` in the core) with `x`, then compute the arm. (Of course, we don't mutate the
167noun, we make a mutant copy.)