aboutsummaryrefslogtreecommitdiff
path: root/doc/fromDyalog.md
blob: 953af3cf7fe1f201c696df7a4e05ec7ee3cede3f (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
*View this file with results and syntax highlighting [here](https://mlochbaum.github.io/BQN/doc/fromDyalog.html).*

# BQN–Dyalog APL dictionary

A few tables to help users of Dyalog APL (or similar) get started quickly on BQN. For a higher-level comparison, check [Why BQN?](../commentary/why.md#versus-apl-and-j). Here we assume `⎕ML` is 1 for Dyalog.

## Terminology

### Array model

BQN uses the [based array model](based.md), so that a Dyalog simple scalar corresponds to many BQN values: an atom, its enclose, and so on.

| Dyalog        | BQN   |
|---------------|-------|
| Simple scalar | Atom  |
| Scalar        | Unit  |
| Vector        | List  |
| Matrix        | Table |

BQN shares the terms "[cell](array.md#cells)" and "major cell" with Dyalog, and uses "element" (which may mean different things to different Dyalog users) *not* for a 0-cell but for the value it contains.

### Roles

Dyalog uses value types (array, function, and so on) to determine syntax while BQN uses a separate concept called syntactic roles. See [context-free grammar](context.md).

| Dyalog type      | BQN role   |
|------------------|------------|
| Array            | Subject    |
| Function         | Function   |
| Monadic operator | 1-modifier |
| Dyadic operator  | 2-modifier |
| Niladic function | *go away*  |

## Syntax

BQN comments are written with `#`, not `⍝`. BQN strings use double quotes `""` while single quotes `''` enclose a character.

BQN's [block](block.md) functions use `{}`, like Dyalog's dfns. The names for inputs and self-reference are different:

| Dyalog | BQN |
|--------|-----|
| `⍺`    | `𝕨` |
| `⍵`    | `𝕩` |
| `∇`    | `𝕊` |
| `⍺⍺`   | `𝔽` |
| `⍵⍵`   | `𝔾` |
| `∇∇`   | `𝕣` |

Blocks don't have guards exactly, but headers and predicates support some similar functionality (first-class functions can also be used for [control structures](control.md)). Headers can also be used to make a block more explicit about its inputs, more like a tradfn.

The assignment arrow `←` defines a new variable in a block, while `↩` modifies an existing one.

BQN uses the ligature character `‿` for stranding, instead of plain juxtaposition. It also has a [list notation](arrayrepr.md#brackets) using `⟨⟩`, and `[]` for higher-rank arrays.

## For reading

Glyphs `+-×÷⌊⌈|⊣⊢⍉` have nearly the same meaning in BQN as APL. The other primitive functions (except `!`, Assert) are translated loosely to Dyalog APL below.

| BQN | Monad         | Dyad
|-----|---------------|-----
| `⋆` | `*`           | `*`
| `√` | `*∘(÷2)`      | `*∘÷⍨`
| `∧` | `{⍵[⍋⍵]}`     | `∧`
| `∨` | `{⍵[⍒⍵]}`     | `∨`
| `¬` | `~`           | `1+-`
| `=` | `≢⍤⍴`         | `=`
| `≠` | `≢`           | `≠`
| `<` | `⊂`           | `<`
| `>` | `↑`           | `>`
| `≢` | `⍴`           | `≢`
| `⥊` | `,`           | `⍴`
| `∾` | `⊃,⌿`         | `⍪`
| `≍` | `↑,⍥⊂`        | `↑,⍥⊂`
| `⋈` | `,⍥⊂`         | `,⍥⊂`
| `↑` | `,⍀`          | `↑`
| `↓` | `{⌽,⍨⍀⌽⍵}`    | `↓`
| `↕` | `⍳`           | `,⌿`
| `»` | ` ≢↑(¯1-≢)↑⊢` | `  ≢⍤⊢↑⍪`
| `«` | `-⍤≢↑(1+≢)↑⊢` | `-⍤≢⍤⊢↑⍪⍨`
| `⌽` | `⊖`           | `⊖`
| `/` | `⍸`           | `⌿`
| `⍋` | `⍋`           | `⍸`
| `⍒` | `⍒`           | `⍸`, reversed order
| `⊏` | `⊣⌿`          | `⌷`
| `⊑` | `⊃`           | `⊃`
| `⊐` | `∪⍳⊢`         | `⍳`
| `⊒` | `+⌿∘.≡⍨∧∘.<⍨∘(⍳≢)` | `{R←≢⍤⊢⍴∘⍋∘⍋⍺⍳⍪⍨⋄⍺(R⍨⍳R)⍵}`
| `∊` | `≠`           | `∊`
| `⍷` | `∪`           | `⍷`
| `⊔` | `{⊂⍵}⌸`       | `{⊂⍵}⌸` or `⊆`

Modifiers are a little harder. Many have equivalents in some cases, but Dyalog sometimes chooses different functionality based on whether the operand is an array. In BQN an array is always treated as a constant function.

| BQN    | `¨` | `⌜`  | `˝` | `` ` `` | ``  | `` | `˜` | ``  | `` | `⟜` |
|:------:|:---:|:----:|:---:|:-------:|:----:|:---:|:---:|:----:|:---:|:---:|
| Dyalog | `¨` | `∘.` | `⌿` |   `⍀`   | `⍤A` | `⍣` | `⍨` | `⍤f` | `⍥` | `∘` |

Some other BQN modifiers have been proposed as future Dyalog extensions:

| BQN             | `⌾` | `⚇` | `⊸` |
|:---------------:|:---:|:---:|:---:|
| Dyalog proposed | `⍢` [Under](https://aplwiki.com/wiki/Under) | `⍥` [Depth](https://aplwiki.com/wiki/Depth_(operator)) | `⍛` [Reverse Compose](https://aplwiki.com/wiki/Reverse_Compose)

## For writing

The tables below give approximate implementations of Dyalog primitives for the ones that aren't the same. First- and last-axis pairs are also mostly omitted. BQN just has the first-axis form, and you can get the last-axis form with `⎉1`.

The form `F⍣G` (Power with a function right operand; Power limit) must be implemented with recursion instead of primitives because it performs unbounded iteration. The modifier `_while_ ← {𝔽⍟𝔾∘𝔽_𝕣_𝔾∘𝔽⍟𝔾𝕩}` provides similar functionality without risk of stack overflow. It's discussed [here](control.md#low-stack-version) and called as `Fn _while_ Cond arg`.

<table>
<tr><th colspan=3>Functions</th></tr>
<tr><th> Glyph          </th><th> Monadic                      </th><th> Dyadic </th>               </tr>
<tr><td> <code>*</code> </td><td colspan=2><code>⋆</code></td>                                      </tr>
<tr><td> <code>⍟</code> </td><td colspan=2><code>⋆⁼</code></td>                                     </tr>
<tr><td> <code>!</code> </td><td><code>×´1+↕</code>            </td><td> <code>(-÷○(×´)1⊸+)⟜↕˜</code></td></tr>
<tr><td> <code>○</code> </td><td> <code>π⊸×</code>             </td><td> <code>•math</code></td>    </tr>
<tr><td> <code>~</code> </td><td> <code>¬</code>               </td><td> <code>¬∘∊/⊣</code></td>    </tr>
<tr><td> <code>?</code> </td><td> <code>•rand.Range⚇0</code>   </td><td> <code>•rand.Deal</code></td></tr>
<tr><td> <code>⍲</code> </td><td>                              </td><td> <code>¬∘∧</code></td>      </tr>
<tr><td> <code>⍱</code> </td><td>                              </td><td> <code>¬∘∨</code></td>      </tr>
<tr><td> <code>⍴</code> </td><td> <code>≢</code>               </td><td> <code>⥊</code></td>        </tr>
<tr><td> <code>,</code> </td><td> <code>⥊</code>               </td><td> <code>∾⎉1</code></td>      </tr>
<tr><td> <code>⍪</code> </td><td> <code>⥊˘</code>              </td><td> <code>∾</code></td>        </tr>
<tr><td> <code>⌽</code> </td><td colspan=2><code>⌽⎉0‿1</code></td>                                  </tr>
<tr><td> <code>↑</code> </td><td> <code>></code>               </td><td> <code>↑</code></td>        </tr>
<tr><td> <code>↓</code> </td><td> <code><˘</code>              </td><td> <code>↓</code></td>        </tr>
<tr><td> <code>⊂</code> </td><td> <code><</code>               </td><td> <code>+`⊸⊔</code></td>     </tr>
<tr><td> <code>⊆</code> </td><td> <code><⍟(1≥≡)</code>         </td><td> <code>(¬-˜⊢×·+`»⊸>)⊸⊔</code></td></tr>
<tr><td> <code>∊</code> </td><td> <code>{(∾𝕊¨)⍟(1<≡)⥊𝕩}</code> </td><td> <code>∊</code></td>        </tr>
<tr><td> <code>⊃</code> </td><td colspan=2><code>⊑</code></td>                                      </tr>
<tr><td> <code>⌿</code> </td><td>                              </td><td> <code>/</code></td>        </tr>
<tr><td> <code>⍀</code> </td><td>                              </td><td> <code>{𝕩⌾(𝕨⊸/)𝕨≠⊸↑0↑𝕩}</code></td></tr>
<tr><td> <code>∩</code> </td><td>                              </td><td> <code>∊/⊣</code></td>      </tr>
<tr><td> <code>∪</code> </td><td> <code>⍷</code>               </td><td> <code>⊣∾∊˜¬⊸/⊢</code></td> </tr>
<tr><td> <code>⍳</code> </td><td> <code>↕</code>               </td><td> <code>⊐</code></td>        </tr>
<tr><td> <code>⍸</code> </td><td> <code>/</code>               </td><td> <code>⍋</code></td>        </tr>
<tr><td> <code>⍋</code> </td><td> <code>⍋</code>               </td><td> <code>⍋⊐</code></td>       </tr>
<tr><td> <code>⍒</code> </td><td> <code>⍒</code>               </td><td> <code>⍒⊐</code></td>       </tr>
<tr><td> <code>≢</code> </td><td> <code>≠</code>               </td><td> <code>≢</code></td>        </tr>
<tr><td> <code>⍎</code> </td><td colspan=2><code>•BQN</code></td>                                   </tr>
<tr><td> <code>⍕</code> </td><td colspan=2><code>•Fmt</code></td>                                   </tr>
<tr><td> <code>⊥</code> </td><td>                              </td><td> <code>{+⟜(𝕨⊸×)´⌽𝕩}</code>    </td></tr>
<tr><td> <code>⊤</code> </td><td>                              </td><td> <code>{𝕨|>⌊∘÷`⌾⌽𝕨«˜<𝕩}</code></td></tr>
<tr><td> <code>⌹</code> </td><td><code>Inverse</code>,         </td><td> <code>Solve</code> from <a href="https://github.com/mlochbaum/bqn-libs/blob/master/matrix.bqn">here</a></td></tr>
<tr><td> <code>⌷</code> </td><td> N/A                          </td><td> <code>⊏</code></td>        </tr>
</table>

<table>
<tr><th colspan=3>Operators</th></tr>
<tr><th> Syntax           </th><th> Monadic          </th><th> Dyadic                </th></tr>
<tr><td> <code>⌿</code>   </td><td> <code>¨˝</code>  </td><td> <code>↕</code>        </td></tr>
<tr><td> <code>⍀</code>   </td><td colspan=2> <code>↑</code>, or <code>`</code> if associative </td></tr>
<tr><td> <code>¨</code>   </td><td colspan=2> <code>¨</code>                         </td></tr>
<tr><td> <code>⍨</code>   </td><td colspan=2> <code>˜</code>                         </td></tr>
<tr><td> <code>⍣</code>   </td><td colspan=2> <code>⍟</code>                         </td></tr>
<tr><td> <code>f.g</code> </td><td>                  </td><td> <code>f˝∘g⎉1‿∞</code> </td></tr>
<tr><td> <code>∘.f</code> </td><td>                  </td><td> <code>f⌜</code>       </td></tr>
<tr><td> <code>A∘g</code> </td><td> <code>A⊸g</code> </td><td>                       </td></tr>
<tr><td> <code>f∘B</code> </td><td> <code>f⟜B</code> </td><td>                       </td></tr>
<tr><td> <code>f∘g</code> </td><td colspan=2> <code>f⟜g</code>                       </td></tr>
<tr><td> <code>f⍤B</code> </td><td colspan=2> <code>f⎉B</code>                       </td></tr>
<tr><td> <code>f⍤g</code> </td><td colspan=2> <code>f∘g</code>                       </td></tr>
<tr><td> <code>f⍥g</code> </td><td colspan=2> <code>f○g</code>                       </td></tr>
<tr><td> <code>f@v</code> </td><td colspan=2> <code>f⌾(v⊸⊏)</code>                   </td></tr>
<tr><td> <code>f⍠B</code> </td><td colspan=2> Uh                                     </td></tr>
<tr><td> <code>f⌸</code>  </td><td><code>⊐⊔↕∘≠</code></td><td><code>⊐⊸⊔</code>       </td></tr>
<tr><td> <code>f⌺B</code> </td><td colspan=2> <code>↕</code>                         </td></tr>
<tr><td> <code>A⌶</code>  </td><td colspan=2> <code>•Something</code>                </td></tr>
<tr><td> <code>f&</code>  </td><td colspan=2> Nothing yet                            </td></tr>
</table>