on master help sign in
Merge pull request #497 from baudtack/master
5e6632drmariani
learn/hoon/workbook/even.mdnew file+54
@@ -0,0 +1,54 @@
1+Write a generator that takes an integer and checks if it even and between 1 and 100.
2+
3+```
4+:- %say
5+|= [* [n=@ud ~] ~]
6+:- %noun
7+?: ?& =(0 (mod n 2))
8+ ?& (gte n 1)
9+ ?! (gth n 100)
10+ ==
11+ ==
12+ %.y
13+%.n
14+```
15+
16+On the very first line, with `:- %say` we are beginning to create a generator of the `%say` kind. The result of a `%say` generator is a cell with a head of `%say` and tail that is a gate, itself producing a `cask`, a pair of a `mark` and some data. For more information about `%say` generators, see the [Generators](/using/generators) documentation.
17+
18+```
19+|= [* [n=@ud ~] ~]
20+```
21+
22+The code above builds a gate. The gate's first argument is a cell provided by Dojo that contains some system information we're not going to use, so we use `*` to indicate "any noun." The next cell is our arguments provided to the generator upon invocation at the `dojo`. Here we only want one `@ud` with the face `n`.
23+
24+```
25+:- %noun
26+```
27+
28+This code is the third line of the `%say` "boilerplate," and it produces a `cask` with the head of `%noun`. We could use any `mark` here, but `%noun` is the most generic type, able to fit any data.
29+
30+Below we'll examine the the series of `?` runes used.
31+
32+```
33+?: ?& =(0 (mod n 2))
34+```
35+
36+`?:` is the simplest "wut" rune. It takes three expressions: a boolean test, a yes-branch, and a no-branch. The yes-branch is executed when the test evaluates to `%.y` and the no-branch is executed when the test evaluates to `%.n`. Here the yes-branch is `%.y` and the no-branch is `%.n`. The boolean test is the more complicated portion. First we're going to use `?&` to combine to expressions with a logical and operation.
37+
38+The first expression is:
39+
40+```
41+=(0 (mod n 2))
42+```
43+
44+which simply asks if `n` is even or not.
45+
46+The second expression is:
47+
48+```
49+ ?& (gte n 1)
50+ ?! (gth n 100)
51+ ==
52+```
53+
54+Again we use the "and" operator on two expressions with `?&` the first is just checking if n is greater than or equal to 1. The second we have artificially use the `?!` rune to demonstrate its use. `?!` is a logical NOT operation. We use that on the result of asking if n is greater than 100 to effectively ask if it is less than or equal to 100.
learn/hoon/workbook/fib.mdnew file+54
@@ -0,0 +1,54 @@
1+In this example, we will write a generator that produces a list of Fibonacci numbers up to `n`.
2+
3+```
4+|= n=@ud
5+%- flop
6+=+ [i=0 p=0 q=1 r=*(list @ud)]
7+|- ^+ r
8+?: =(i n) r
9+%= $
10+ i +(i)
11+ p q
12+ q (add p q)
13+ r [q r]
14+==
15+```
16+
17+On the first line, we use `|=` to produce a gate which takes an `@ud` that's stored in the face `n`. This `n` sample that we give our gate determines how long our Fibonacci sequence is. When the list that our program builds has `n` members, the program ends.
18+
19+```
20+%- flop
21+```
22+
23+In the line above, we use `flop` on the output of the rest of the program. `flop` is a standard library function to reverse a list.
24+
25+Why are we using this instead of just producing the list in the order we want it in the first place? Because with lists, adding an element to the end is a computationally expensive operation that gets more expensive the longer the list is, due to the fact that you need to traverse to the end of the tree. Adding an element to the front, however, is cheap. [In Big-O Notation](https://en.wikipedia.org/wiki/Big_O_notation), adding to the end of a list is O(n) and the front is O(1).
26+
27+```
28+=+ [i=0 p=0 q=1 r=*(list @ud)]
29+```
30+
31+Here we declare several values that we are going to use the execution of our program. The only one of these that is noteworthy is `r`: we're using `*` to bunt, or get the default value for, the mold `(list @ud)`.
32+
33+```
34+|- ^+ r
35+```
36+
37+With this code, we define `|-`, the _trap_ that acts as a recursion point and contains the rest of our program. We also use `^+` to cast the output by example. This will result in the output being the same type as `r`, a list of `@ud`.
38+
39+```
40+?: =(i n) r
41+```
42+
43+In the code above, `?:` checks whether the first child, `=(i n)`, our terminating case, is true or false. If it is true, it branches to `r` and the program ends. If it is false, the program continues to the code below.
44+
45+```
46+%= $
47+ i +(i)
48+ p q
49+ q (add p q)
50+ r [q r]
51+==
52+```
53+
54+The final expression in our program calls the `$` arm of the trap we are but makes some changes: we increment `i`, set `p` to be `q` and `q` becomes the sum of `p` and `q`. `r` becomes a cell of `q` and whatever `r` was previously. The list built from this is the one that will get `flop`ped to produce the result at the end of the computation.