Skip to content

Commit 9452c97

Browse files
Two extra concept exercises (#180)
1 parent a4b4cd4 commit 9452c97

32 files changed

Lines changed: 499 additions & 27 deletions

File tree

concepts/sequences/about.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,8 @@ with the others.
1313
| `nth` | `( n seq -- elt )` (0-based) |
1414
| `head` | `( seq n -- headseq )` |
1515
| `tail` | `( seq n -- tailseq )` |
16+
| `pad-head` | `( seq n elt -- padded )` |
17+
| `pad-tail` | `( seq n elt -- padded )` |
1618
| `prefix` | `( seq elt -- newseq )` |
1719
| `suffix` | `( seq elt -- newseq )` |
1820
| `unclip` | `( seq -- rest first )` |
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
{
2+
"authors": [
3+
"keiravillekode"
4+
],
5+
"blurb": "Build a sequence index by index using <iota> + map, and turn it into a string with >string."
6+
}

concepts/tabulation/about.md

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
# About
2+
3+
Factor's `<iota>` produces a *virtual* sequence of the integers
4+
`0, 1, …, n-1`. Walking it with `map` yields a tabulated sequence
5+
where each element is a function of its position:
6+
7+
```factor
8+
USING: math sequences ;
9+
10+
5 <iota> [ sq ] map . ! => { 0 1 4 9 16 }
11+
8 <iota> [ 1 + ] map . ! => { 1 2 3 4 5 6 7 8 }
12+
```
13+
14+
Two pieces let you turn a sequence of integer codes into a
15+
string:
16+
17+
| word | role |
18+
|-----------|---------------------------------------------------------|
19+
| `CHAR:` | parse-time literal that pushes a character's code point |
20+
| `>string` | convert a sequence of code points to a string |
21+
22+
Combined, they form the standard idiom for building a row of
23+
characters indexed by position:
24+
25+
```factor
26+
USING: kernel math sequences strings ;
27+
28+
10 <iota> [ 2 mod zero? [ CHAR: O ] [ CHAR: . ] if ] map >string .
29+
! => "O.O.O.O.O."
30+
```
31+
32+
Choosing the character with `if` (or `?`) inside the quotation
33+
keeps the per-position decision close to the index it depends on.
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
# Introduction
2+
3+
When you need a sequence of `n` values where each one depends on
4+
its index, Factor gives you `<iota>` — a virtual sequence of the
5+
integers `0, 1, …, n-1` — and `map`:
6+
7+
```factor
8+
USING: math sequences ;
9+
10+
5 <iota> [ 2 * ] map . ! => { 0 2 4 6 8 }
11+
```
12+
13+
`<iota>` doesn't allocate the integers up front; `map` walks
14+
through them in order, applying the quotation to each.
15+
16+
If the per-position result is a character code, `>string` turns
17+
the result into a string — the natural way to assemble a row of
18+
characters from index-driven decisions:
19+
20+
```factor
21+
USING: strings ;
22+
23+
5 <iota> [ CHAR: a + ] map >string . ! => "abcde"
24+
```
25+
26+
[strings]: https://docs.factorcode.org/content/article-strings.html

concepts/tabulation/links.json

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
[
2+
{
3+
"url": "https://docs.factorcode.org/content/article-sequences.html",
4+
"description": "Sequences — Factor handbook"
5+
},
6+
{
7+
"url": "https://docs.factorcode.org/content/article-strings.html",
8+
"description": "Strings — Factor handbook"
9+
}
10+
]

config.json

Lines changed: 23 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -129,6 +129,20 @@
129129
],
130130
"status": "beta"
131131
},
132+
{
133+
"slug": "bunting-builder",
134+
"name": "Brooke's Bunting Builder",
135+
"uuid": "f7c75218-7eb2-4985-9efe-f6cfd5a04b45",
136+
"concepts": [
137+
"tabulation"
138+
],
139+
"prerequisites": [
140+
"quotations",
141+
"strings",
142+
"conditionals"
143+
],
144+
"status": "beta"
145+
},
132146
{
133147
"slug": "backyard-birdwatcher",
134148
"name": "Backyard Birdwatcher",
@@ -138,7 +152,8 @@
138152
],
139153
"prerequisites": [
140154
"stack-effect",
141-
"conditionals"
155+
"conditionals",
156+
"tabulation"
142157
],
143158
"status": "beta"
144159
},
@@ -899,7 +914,8 @@
899914
"strings",
900915
"higher-order-sequences",
901916
"unicode",
902-
"locals"
917+
"locals",
918+
"quotations-call"
903919
],
904920
"difficulty": 5
905921
},
@@ -1226,6 +1242,11 @@
12261242
"slug": "bitwise-operations",
12271243
"name": "Bitwise Operations"
12281244
},
1245+
{
1246+
"uuid": "0e95ebe8-0b9c-4b52-8f84-f3f04fc2fd83",
1247+
"slug": "tabulation",
1248+
"name": "Tabulation"
1249+
},
12291250
{
12301251
"uuid": "638e8893-fd14-4448-87c8-13029851f225",
12311252
"slug": "sequences",

exercises/concept/backyard-birdcount/.docs/introduction.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -81,8 +81,8 @@ prefix ( seq elt -- newseq )
8181
```
8282

8383
```factor
84-
{ 0 2 } 5 prefix .
85-
! => { 5 0 2 }
84+
{ 7 9 } 3 prefix .
85+
! => { 3 7 9 }
8686
```
8787

8888
[sequences]: https://docs.factorcode.org/content/vocab-sequences.html

exercises/concept/backyard-birdwatcher/.docs/hints.md

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,5 +32,12 @@
3232
- `count` takes a sequence and a predicate, like `any?` does, but
3333
returns *how many* elements matched.
3434

35+
## 6. Pad missing days
36+
37+
- `pad-tail` takes a sequence, a target length, and a fill element,
38+
and extends the sequence to that length by appending copies of
39+
the element. If the sequence is already long enough, it is
40+
returned unchanged.
41+
3542
[sequences]: https://docs.factorcode.org/content/vocab-sequences.html
3643
[math.statistics]: https://docs.factorcode.org/content/vocab-math.statistics.html

exercises/concept/backyard-birdwatcher/.docs/instructions.md

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -56,3 +56,20 @@ return the number of busy days in the array.
5656
{ 2 5 0 7 4 1 } busy-days .
5757
! => 2
5858
```
59+
60+
## 6. Pad missing days
61+
62+
If you didn't watch on every day of an `n`-day stretch, fill the
63+
missing trailing days with `0`. Define `pad-missing-days` to take
64+
an array of counts and a target length `n`, and return an array
65+
of length at least `n` whose extra slots are `0`. Existing counts
66+
must be preserved unchanged; if the input is already at least `n`
67+
long, return it unchanged.
68+
69+
```factor
70+
{ 2 5 0 } 7 pad-missing-days .
71+
! => { 2 5 0 0 0 0 0 }
72+
73+
{ 4 1 6 8 } 3 pad-missing-days .
74+
! => { 4 1 6 8 }
75+
```

exercises/concept/backyard-birdwatcher/.docs/introduction.md

Lines changed: 30 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,32 @@ tail ( seq n -- tailseq ) ! drop first n
4444
{ 1 2 3 4 5 } 3 tail . ! => { 4 5 }
4545
```
4646

47+
## Padding
48+
49+
```
50+
pad-head ( seq n elt -- padded ) ! prepend copies of elt
51+
pad-tail ( seq n elt -- padded ) ! append copies of elt
52+
```
53+
54+
Both extend `seq` until its length is at least `n`. If `seq` is
55+
already that long, it is returned unchanged.
56+
57+
```factor
58+
{ 2 5 0 } 6 0 pad-tail . ! => { 2 5 0 0 0 0 }
59+
{ 4 1 } 5 9 pad-head . ! => { 9 9 9 4 1 }
60+
```
61+
62+
## The same words work on strings
63+
64+
A string is a sequence of characters, so everything above works on
65+
strings too — the result is just another string instead of an array:
66+
67+
```factor
68+
"hello" length . ! => 5
69+
"hello" 3 head . ! => "hel"
70+
"abc" 6 CHAR: . pad-tail . ! => "abc..."
71+
```
72+
4773
## Aggregating
4874

4975
`sum` (in [`math.statistics`][math.statistics]) adds the elements of
@@ -61,7 +87,7 @@ count ( seq quot -- n )
6187
```
6288

6389
```factor
64-
{ 2 5 0 7 4 1 } [ 5 >= ] count . ! => 2
90+
{ 2 5 0 7 4 1 } [ even? ] count . ! => 3
6591
```
6692

6793
## Predicates over the whole sequence
@@ -73,7 +99,7 @@ empty? ( seq -- ? )
7399
```
74100

75101
```factor
76-
{ 2 5 0 7 } [ zero? ] any? . ! => t
102+
{ 2 5 0 7 } [ 4 > ] any? . ! => t
77103
{ 2 5 0 7 } [ 0 > ] all? . ! => f
78104
```
79105

@@ -89,8 +115,8 @@ suffix ( seq elt -- newseq )
89115
```
90116

91117
```factor
92-
{ 2 5 0 7 4 1 } unclip-last 1 + suffix .
93-
! => { 2 5 0 7 4 2 }
118+
{ 10 20 30 } unclip-last 2 * suffix .
119+
! => { 10 20 60 }
94120
```
95121

96122
[sequences]: https://docs.factorcode.org/content/vocab-sequences.html

0 commit comments

Comments
 (0)