@effekt-lang/effekt 0.3.0 → 0.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (44) hide show
  1. package/README.md +6 -18
  2. package/bin/effekt +0 -0
  3. package/libraries/common/args.effekt +0 -27
  4. package/libraries/common/array.effekt +34 -63
  5. package/libraries/common/bench.effekt +40 -22
  6. package/libraries/common/buffer.effekt +8 -20
  7. package/libraries/common/bytes.effekt +5 -15
  8. package/libraries/common/dequeue.effekt +5 -5
  9. package/libraries/common/effekt.effekt +51 -92
  10. package/libraries/common/exception.effekt +0 -1
  11. package/libraries/common/io/console.effekt +30 -36
  12. package/libraries/common/io/error.effekt +131 -30
  13. package/libraries/common/io/filesystem.effekt +262 -0
  14. package/libraries/common/io/network.effekt +30 -54
  15. package/libraries/common/io/time.effekt +9 -12
  16. package/libraries/common/io.effekt +54 -124
  17. package/libraries/common/list.effekt +345 -327
  18. package/libraries/common/process.effekt +0 -1
  19. package/libraries/common/queue.effekt +1 -3
  20. package/libraries/common/ref.effekt +11 -24
  21. package/libraries/common/result.effekt +6 -14
  22. package/libraries/common/seq.effekt +28 -49
  23. package/libraries/common/string/tty.effekt +66 -0
  24. package/libraries/common/string.effekt +7 -49
  25. package/libraries/common/test.effekt +96 -34
  26. package/libraries/js/unsafe/cont.effekt +1 -1
  27. package/libraries/llvm/io.c +258 -378
  28. package/libraries/llvm/main.c +3 -0
  29. package/libraries/llvm/rts.ll +57 -38
  30. package/libraries/llvm/types.c +10 -1
  31. package/licenses/eclipse public license, version 2.0 - epl-2.0.html +4 -4
  32. package/licenses/mit license - mit-license.html +21 -20
  33. package/licenses/the bsd license - bsd-license.html +20 -21
  34. package/licenses/the mit license - mit.html +22 -21
  35. package/package.json +1 -1
  36. package/libraries/chez/lift/effekt.ss +0 -118
  37. package/libraries/common/io/files.effekt +0 -282
  38. package/libraries/js/io.js +0 -143
  39. package/libraries/llvm/io.ll +0 -19
  40. package/libraries/ml/effekt.sml +0 -65
  41. package/libraries/ml/internal/mllist.effekt +0 -9
  42. package/libraries/ml/internal/mloption.effekt +0 -18
  43. package/libraries/ml/random.effekt +0 -85
  44. package/libraries/ml/text/regex.effekt +0 -102
@@ -4,32 +4,32 @@ import effekt
4
4
  import option
5
5
  import exception
6
6
 
7
- // Immutable linked list for finite sequences of elements.
7
+ /// Immutable linked list for finite sequences of elements.
8
8
  type List[A] {
9
9
  Nil();
10
10
  Cons(head: A, tail: List[A])
11
11
  }
12
12
 
13
- // Create an empty list.
14
- //
15
- // O(1)
13
+ /// Create an empty list.
14
+ ///
15
+ /// O(1)
16
16
  def empty[A](): List[A] = Nil()
17
17
 
18
- // Create a list with one element.
19
- //
20
- // O(1)
18
+ /// Create a list with one element.
19
+ ///
20
+ /// O(1)
21
21
  def singleton[A](x: A): List[A] = Cons(x, Nil())
22
22
 
23
- // Create a list of length `size` where all elements are `default`.
24
- //
25
- // O(size)
23
+ /// Create a list of length `size` where all elements are `default`.
24
+ ///
25
+ /// O(size)
26
26
  def fill[A](size: Int, default: A): List[A] = {
27
27
  build(size) { i => default }
28
28
  }
29
29
 
30
- // Create a list from a function `index` of given `size`.
31
- //
32
- // O(size)
30
+ /// Create a list from a function `index` of given `size`.
31
+ ///
32
+ /// O(size)
33
33
  def build[A](size: Int) { index: Int => A }: List[A] = {
34
34
  var result = empty()
35
35
  each(0, size) { i =>
@@ -38,52 +38,52 @@ def build[A](size: Int) { index: Int => A }: List[A] = {
38
38
  result.reverse
39
39
  }
40
40
 
41
- // Check if list is empty.
42
- //
43
- // O(1)
41
+ /// Check if list is empty.
42
+ ///
43
+ /// O(1)
44
44
  def isEmpty[A](l: List[A]): Bool = l match {
45
45
  case Nil() => true
46
46
  case Cons(a, rest) => false
47
47
  }
48
48
 
49
- // Check if list is nonempty.
50
- //
51
- // O(1)
49
+ /// Check if list is nonempty.
50
+ ///
51
+ /// O(1)
52
52
  def nonEmpty[A](l: List[A]): Bool = l match {
53
53
  case Nil() => false
54
54
  case Cons(a, rest) => true
55
55
  }
56
56
 
57
- // Return the first element of a given list.
58
- // Throws a `MissingValue` exception if it's empty.
59
- //
60
- // O(1)
57
+ /// Return the first element of a given list.
58
+ /// Throws a `MissingValue` exception if it's empty.
59
+ ///
60
+ /// O(1)
61
61
  def head[A](l: List[A]): A / Exception[MissingValue] = l match {
62
62
  case Nil() => do raise(MissingValue(), "Trying to get the head of an empty list")
63
63
  case Cons(a, rest) => a
64
64
  }
65
65
 
66
- // Return all elements of a given list except the first element.
67
- // Throws a `MissingValue` exception if it's empty.
68
- //
69
- // O(1)
66
+ /// Return all elements of a given list except the first element.
67
+ /// Throws a `MissingValue` exception if it's empty.
68
+ ///
69
+ /// O(1)
70
70
  def tail[A](l: List[A]): List[A] / Exception[MissingValue] = l match {
71
71
  case Nil() => do raise(MissingValue(), "Trying to get the head of an empty list")
72
72
  case Cons(a, rest) => rest
73
73
  }
74
74
 
75
- // Return the first element of a given list.
76
- // Returns `None()` if it's empty.
77
- //
78
- // O(1)
75
+ /// Return the first element of a given list.
76
+ /// Returns `None()` if it's empty.
77
+ ///
78
+ /// O(1)
79
79
  def headOption[A](l: List[A]): Option[A] = l match {
80
80
  case Nil() => None()
81
81
  case Cons(a, rest) => Some(a)
82
82
  }
83
83
 
84
- // Returns the last element of a given list.
85
- //
86
- // O(N)
84
+ /// Returns the last element of a given list.
85
+ ///
86
+ /// O(N)
87
87
  def last[A](l: List[A]): A / Exception[MissingValue] = {
88
88
  def go(list: List[A]): A = {
89
89
  list match {
@@ -96,9 +96,9 @@ def last[A](l: List[A]): A / Exception[MissingValue] = {
96
96
  go(l)
97
97
  }
98
98
 
99
- // Get the value at given index.
100
- //
101
- // O(N)
99
+ /// Get the value at given index.
100
+ ///
101
+ /// O(N)
102
102
  def get[A](list: List[A], index: Int): A / Exception[OutOfBounds] = {
103
103
  def go(list: List[A], i: Int): A = {
104
104
  list match {
@@ -111,17 +111,17 @@ def get[A](list: List[A], index: Int): A / Exception[OutOfBounds] = {
111
111
  go(list, index)
112
112
  }
113
113
 
114
- // Traverse a list, applying the given action on every element.
115
- //
116
- // O(N)
114
+ /// Traverse a list, applying the given action on every element.
115
+ ///
116
+ /// O(N)
117
117
  def foreach[A](l: List[A]) { f: (A) => Unit } : Unit = l match {
118
118
  case Nil() => ()
119
119
  case Cons(head, tail) => f(head); tail.foreach {f}
120
120
  }
121
121
 
122
- // Traverse a list, applying the given action on every element.
123
- //
124
- // O(N)
122
+ /// Traverse a list, applying the given action on every element.
123
+ ///
124
+ /// O(N)
125
125
  def foreach[A](l: List[A]) { f: (A) {Control} => Unit } : Unit = {
126
126
  var remainder = l
127
127
  loop { {label} =>
@@ -134,9 +134,9 @@ def foreach[A](l: List[A]) { f: (A) {Control} => Unit } : Unit = {
134
134
  }
135
135
  }
136
136
 
137
- // Traverse a list, applying the given action on every element and its (zero-based) index.
138
- //
139
- // O(N)
137
+ /// Traverse a list, applying the given action on every element and its (zero-based) index.
138
+ ///
139
+ /// O(N)
140
140
  def foreachIndex[A](list: List[A]){ f: (Int, A) => Unit }: Unit = {
141
141
  def loop(index: Int, remainder: List[A]): Unit = remainder match {
142
142
  case Nil() => ()
@@ -147,9 +147,9 @@ def foreachIndex[A](list: List[A]){ f: (Int, A) => Unit }: Unit = {
147
147
  loop(0, list)
148
148
  }
149
149
 
150
- // Traverse a list, applying the given action on every element and its (zero-based) index.
151
- //
152
- // O(N)
150
+ /// Traverse a list, applying the given action on every element and its (zero-based) index.
151
+ ///
152
+ /// O(N)
153
153
  def foreachIndex[A](list: List[A]){ f: (Int, A) {Control} => Unit }: Unit = {
154
154
  var remainder = list
155
155
  var i = -1
@@ -164,20 +164,20 @@ def foreachIndex[A](list: List[A]){ f: (Int, A) {Control} => Unit }: Unit = {
164
164
  }
165
165
  }
166
166
 
167
- // Map a function `f` over elements in a given list.
168
- //
169
- // O(N)
167
+ /// Map a function `f` over elements in a given list.
168
+ ///
169
+ /// O(N)
170
170
  def map[A, B](l: List[A]) { f: A => B } : List[B] = {
171
171
  var acc = Nil[B]()
172
172
  l.foreach { el => acc = Cons(f(el), acc) }
173
173
  acc.reverse
174
174
  }
175
175
 
176
- // Map a function `f` over elements in a given list,
177
- // keeping only the elements for which the function returned `Some(...)`,
178
- // discarding the elements for which the function returned `None()`.
179
- //
180
- // O(N)
176
+ /// Map a function `f` over elements in a given list,
177
+ /// keeping only the elements for which the function returned `Some(...)`,
178
+ /// discarding the elements for which the function returned `None()`.
179
+ ///
180
+ /// O(N)
181
181
  def collect[A, B](l: List[A]) { f : A => Option[B] }: List[B] = {
182
182
  var acc = Nil[B]()
183
183
  l.foreach { a =>
@@ -190,9 +190,9 @@ def collect[A, B](l: List[A]) { f : A => Option[B] }: List[B] = {
190
190
  acc.reverse
191
191
  }
192
192
 
193
- // Map a function `f` over elements in a given list and concatenate the results.
194
- //
195
- // O(N)
193
+ /// Map a function `f` over elements in a given list and concatenate the results.
194
+ ///
195
+ /// O(N)
196
196
  def flatMap[A, B](l: List[A]) { f : A => List[B] }: List[B] = {
197
197
  var acc = Nil[B]()
198
198
  l.foreach { a =>
@@ -202,9 +202,9 @@ def flatMap[A, B](l: List[A]) { f : A => List[B] }: List[B] = {
202
202
  acc
203
203
  }
204
204
 
205
- // Check if predicate is true for all elements of the given list.
206
- //
207
- // O(N)
205
+ /// Check if predicate is true for all elements of the given list.
206
+ ///
207
+ /// O(N)
208
208
  def all[A](list: List[A]) { predicate: A => Bool }: Bool = {
209
209
  list match {
210
210
  case Cons(x, xs) => predicate(x) && all(xs) { predicate }
@@ -212,9 +212,9 @@ def all[A](list: List[A]) { predicate: A => Bool }: Bool = {
212
212
  }
213
213
  }
214
214
 
215
- // Check if predicate is true for at least one element of the given list.
216
- //
217
- // O(N)
215
+ /// Check if predicate is true for at least one element of the given list.
216
+ ///
217
+ /// O(N)
218
218
  def any[A](list: List[A]) { predicate: A => Bool }: Bool = {
219
219
  list match {
220
220
  case Cons(x, xs) => predicate(x) || any(xs) { predicate }
@@ -222,71 +222,89 @@ def any[A](list: List[A]) { predicate: A => Bool }: Bool = {
222
222
  }
223
223
  }
224
224
 
225
- // Sum the elements of the list.
226
- //
227
- // O(N)
225
+ /// Fold a list using `f`, starting from the left given a starting value.
226
+ ///
227
+ /// O(N)
228
+ def foldLeft[A, B](l: List[A], init: B) { f: (B, A) => B }: B = {
229
+ var acc = init;
230
+ l.foreach { x => acc = f(acc, x) };
231
+ acc
232
+ }
233
+
234
+ /// Fold a list using `f`, starting from the right given a starting value.
235
+ ///
236
+ /// O(N)
237
+ def foldRight[A, B](l: List[A], init: B) { f: (A, B) => B }: B = {
238
+ var acc = init;
239
+ l.reverse.foreach { x => acc = f(x, acc) };
240
+ acc
241
+ }
242
+
243
+ /// Sum the elements of the list.
244
+ ///
245
+ /// O(N)
228
246
  def sum(list: List[Int]): Int = {
229
247
  var n = 0;
230
248
  list.foreach { x => n = n + x };
231
249
  n
232
250
  }
233
251
 
234
- // Calculate the size of the list.
235
- //
236
- // O(N)
252
+ /// Calculate the size of the list.
253
+ ///
254
+ /// O(N)
237
255
  def size[A](l: List[A]): Int = {
238
256
  var n = 0;
239
257
  l.foreach { _ => n = n + 1 };
240
258
  n
241
259
  }
242
260
 
243
- // Reverse the list.
244
- //
245
- // O(N)
261
+ /// Reverse the list.
262
+ ///
263
+ /// O(N)
246
264
  def reverse[A](l: List[A]): List[A] = {
247
265
  var res = Nil[A]()
248
266
  l.foreach { el => res = Cons(el, res) }
249
267
  res
250
268
  }
251
269
 
252
- // Reverse a list `l` and append `other` to it.
253
- //
254
- // Example:
255
- // ```
256
- // > [1,2,3].reverseOnto([4,5,6])
257
- // [3,2,1,4,5,6]
258
- // ```
259
- //
260
- // O(|l|)
270
+ /// Reverse a list `l` and append `other` to it.
271
+ ///
272
+ /// Example:
273
+ /// ```
274
+ /// > [1,2,3].reverseOnto([4,5,6])
275
+ /// [3,2,1,4,5,6]
276
+ /// ```
277
+ ///
278
+ /// O(|l|)
261
279
  def reverseOnto[A](l: List[A], other: List[A]): List[A] = l match {
262
280
  case Nil() => other
263
281
  case Cons(a, rest) => rest.reverseOnto(Cons(a, other))
264
282
  }
265
283
 
266
- // Concatenate list `l` with list `other`:
267
- //
268
- // Example:
269
- // ```
270
- // > [1,2,3].append([4,5,6])
271
- // [1,2,3,4,5,6]
272
- // ```
273
- //
274
- // O(N)
284
+ /// Concatenate list `l` with list `other`:
285
+ ///
286
+ /// Example:
287
+ /// ```
288
+ /// > [1,2,3].append([4,5,6])
289
+ /// [1,2,3,4,5,6]
290
+ /// ```
291
+ ///
292
+ /// O(N)
275
293
  def append[A](l: List[A], other: List[A]): List[A] =
276
294
  l.reverse.reverseOnto(other)
277
295
 
278
- // Flatten a list of lists into a single list.
279
- //
280
- // Examples:
281
- // ```
282
- // > [[1, 2, 3], [4, 5], [6]].join()
283
- // [1, 2, 3, 4, 5, 6]
284
- //
285
- // > [[]].join()
286
- // []
287
- // ```
288
- //
289
- // O(N)
296
+ /// Flatten a list of lists into a single list.
297
+ ///
298
+ /// Examples:
299
+ /// ```
300
+ /// > [[1, 2, 3], [4, 5], [6]].join()
301
+ /// [1, 2, 3, 4, 5, 6]
302
+ ///
303
+ /// > [[]].join()
304
+ /// []
305
+ /// ```
306
+ ///
307
+ /// O(N)
290
308
  def join[A](lists: List[List[A]]): List[A] = {
291
309
  var acc: List[A] = Nil()
292
310
  lists.foreach { list =>
@@ -295,19 +313,19 @@ def join[A](lists: List[List[A]]): List[A] = {
295
313
  acc
296
314
  }
297
315
 
298
- // Flatten a list of lists into a single list,
299
- // putting the `between` list in between each list in the input.
300
- //
301
- // Examples:
302
- // ```
303
- // > [[100], [200, 300], [400]].join([1, 2, 3])
304
- // [100, 1, 2, 3, 200, 300, 1, 2, 3, 400]
305
- //
306
- // > [[]].join([1, 2, 3])
307
- // []
308
- // ```
309
- //
310
- // O(N)
316
+ /// Flatten a list of lists into a single list,
317
+ /// putting the `between` list in between each list in the input.
318
+ ///
319
+ /// Examples:
320
+ /// ```
321
+ /// > [[100], [200, 300], [400]].join([1, 2, 3])
322
+ /// [100, 1, 2, 3, 200, 300, 1, 2, 3, 400]
323
+ ///
324
+ /// > [[]].join([1, 2, 3])
325
+ /// []
326
+ /// ```
327
+ ///
328
+ /// O(N)
311
329
  def join[A](lists: List[List[A]], between: List[A]): List[A] = {
312
330
  lists match {
313
331
  case Nil() => Nil()
@@ -318,27 +336,27 @@ def join[A](lists: List[List[A]], between: List[A]): List[A] = {
318
336
  }
319
337
  }
320
338
 
321
- // Take the first `n` elements of a given list.
322
- //
323
- // Examples:
324
- // ```
325
- // > [1, 2, 3].take(2)
326
- // [1, 2]
327
- //
328
- // > [1, 2, 3].take(0)
329
- // []
330
- //
331
- // > [1, 2, 3].take(3)
332
- // [1, 2, 3]
333
- //
334
- // > [1, 2, 3].take(5)
335
- // [1, 2, 3]
336
- //
337
- // > [1, 2, 3].take(-1)
338
- // []
339
- // ```
340
- //
341
- // O(n)
339
+ /// Take the first `n` elements of a given list.
340
+ ///
341
+ /// Examples:
342
+ /// ```
343
+ /// > [1, 2, 3].take(2)
344
+ /// [1, 2]
345
+ ///
346
+ /// > [1, 2, 3].take(0)
347
+ /// []
348
+ ///
349
+ /// > [1, 2, 3].take(3)
350
+ /// [1, 2, 3]
351
+ ///
352
+ /// > [1, 2, 3].take(5)
353
+ /// [1, 2, 3]
354
+ ///
355
+ /// > [1, 2, 3].take(-1)
356
+ /// []
357
+ /// ```
358
+ ///
359
+ /// O(n)
342
360
  def take[A](l: List[A], n: Int): List[A] =
343
361
  if (n <= 0) {
344
362
  Nil()
@@ -347,27 +365,27 @@ def take[A](l: List[A], n: Int): List[A] =
347
365
  case Cons(a, rest) => Cons(a, rest.take(n - 1))
348
366
  }
349
367
 
350
- // Drop the first `n` elements of a given list.
351
- //
352
- // Examples:
353
- // ```
354
- // > [1, 2, 3].drop(2)
355
- // [3]
356
- //
357
- // > [1, 2, 3].drop(0)
358
- // [1, 2, 3]
359
- //
360
- // > [1, 2, 3].drop(3)
361
- // []
362
- //
363
- // > [1, 2, 3].drop(5)
364
- // []
365
- //
366
- // > [1, 2, 3].drop(-1)
367
- // [1, 2, 3]
368
- // ```
369
- //
370
- // O(n)
368
+ /// Drop the first `n` elements of a given list.
369
+ ///
370
+ /// Examples:
371
+ /// ```
372
+ /// > [1, 2, 3].drop(2)
373
+ /// [3]
374
+ ///
375
+ /// > [1, 2, 3].drop(0)
376
+ /// [1, 2, 3]
377
+ ///
378
+ /// > [1, 2, 3].drop(3)
379
+ /// []
380
+ ///
381
+ /// > [1, 2, 3].drop(5)
382
+ /// []
383
+ ///
384
+ /// > [1, 2, 3].drop(-1)
385
+ /// [1, 2, 3]
386
+ /// ```
387
+ ///
388
+ /// O(n)
371
389
  def drop[A](l: List[A], n: Int): List[A] =
372
390
  if (n <= 0) {
373
391
  l
@@ -376,57 +394,57 @@ def drop[A](l: List[A], n: Int): List[A] =
376
394
  case Cons(a, rest) => rest.drop(n - 1)
377
395
  }
378
396
 
379
- // Return a slice of a given list from the starting index (inclusive)
380
- // to the given end index (exclusive).
381
- //
382
- // Examples:
383
- // ```
384
- // > [1, 2, 3, 4, 5, 6].slice(1, 4)
385
- // [2, 3, 4]
386
- //
387
- // > [1, 2, 3, 4, 5, 6].slice(1, 2)
388
- // [2]
389
- //
390
- // > [1, 2, 3, 4, 5, 6].slice(1, 1)
391
- // []
392
- //
393
- // > [1, 2, 3, 4, 5, 6].slice(4, 1)
394
- // []
395
- //
396
- // > [1, 2, 3, 4, 5, 6].slice(-100, 100)
397
- // [1, 2, 3, 4, 5, 6]
398
- // ```
399
- //
400
- // O(N)
397
+ /// Return a slice of a given list from the starting index (inclusive)
398
+ /// to the given end index (exclusive).
399
+ ///
400
+ /// Examples:
401
+ /// ```
402
+ /// > [1, 2, 3, 4, 5, 6].slice(1, 4)
403
+ /// [2, 3, 4]
404
+ ///
405
+ /// > [1, 2, 3, 4, 5, 6].slice(1, 2)
406
+ /// [2]
407
+ ///
408
+ /// > [1, 2, 3, 4, 5, 6].slice(1, 1)
409
+ /// []
410
+ ///
411
+ /// > [1, 2, 3, 4, 5, 6].slice(4, 1)
412
+ /// []
413
+ ///
414
+ /// > [1, 2, 3, 4, 5, 6].slice(-100, 100)
415
+ /// [1, 2, 3, 4, 5, 6]
416
+ /// ```
417
+ ///
418
+ /// O(N)
401
419
  def slice[A](list: List[A], start: Int, stopExclusive: Int): List[A] = {
402
420
  val prefix = list.drop(start)
403
421
  val length = stopExclusive - start
404
422
  prefix.take(length)
405
423
  }
406
424
 
407
- // Split the list at given index.
408
- //
409
- // Law: `val (l, r) = list.splitAt(i); l.append(r) === list`
410
- //
411
- // O(N)
425
+ /// Split the list at given index.
426
+ ///
427
+ /// Law: `val (l, r) = list.splitAt(i); l.append(r) === list`
428
+ ///
429
+ /// O(N)
412
430
  def splitAt[A](list: List[A], index: Int): (List[A], List[A]) = {
413
431
  (list.take(index), list.drop(index))
414
432
  }
415
433
 
416
- // Update the element at given index in the list using the `update` function.
417
- // Returns the original list if the index is out of bounds.
418
- //
419
- // See: `modifyAt`
420
- // Examples:
421
- // ```
422
- // > [1, 2, 3].updateAt(1) { n => n + 100 }
423
- // [1, 102, 3]
424
- //
425
- // > [1, 2, 3].updateAt(10) { n => n + 100 }
426
- // [1, 2, 3]
427
- // ```
428
- //
429
- // O(N)
434
+ /// Update the element at given index in the list using the `update` function.
435
+ /// Returns the original list if the index is out of bounds.
436
+ ///
437
+ /// See: `modifyAt`
438
+ /// Examples:
439
+ /// ```
440
+ /// > [1, 2, 3].updateAt(1) { n => n + 100 }
441
+ /// [1, 102, 3]
442
+ ///
443
+ /// > [1, 2, 3].updateAt(10) { n => n + 100 }
444
+ /// [1, 2, 3]
445
+ /// ```
446
+ ///
447
+ /// O(N)
430
448
  def updateAt[A](list: List[A], index: Int) { update: A => A }: List[A] = {
431
449
  list.splitAt(index) match {
432
450
  case (left, Cons(x, right)) =>
@@ -435,20 +453,20 @@ def updateAt[A](list: List[A], index: Int) { update: A => A }: List[A] = {
435
453
  }
436
454
  }
437
455
 
438
- // Modify the element at given index in the list using the `update` function.
439
- // Throws `OutOfBounds` if the index is out of bounds.
440
- //
441
- // See: `updateAt`
442
- // Examples:
443
- // ```
444
- // > [1, 2, 3].modifyAt(1) { n => n + 100 }
445
- // Some([1, 102, 3])
446
- //
447
- // > [1, 2, 3].modifyAt(10) { n => n + 100 }
448
- // None()
449
- // ```
450
- //
451
- // O(N)
456
+ /// Modify the element at given index in the list using the `update` function.
457
+ /// Throws `OutOfBounds` if the index is out of bounds.
458
+ ///
459
+ /// See: `updateAt`
460
+ /// Examples:
461
+ /// ```
462
+ /// > [1, 2, 3].modifyAt(1) { n => n + 100 }
463
+ /// Some([1, 102, 3])
464
+ ///
465
+ /// > [1, 2, 3].modifyAt(10) { n => n + 100 }
466
+ /// None()
467
+ /// ```
468
+ ///
469
+ /// O(N)
452
470
  def modifyAt[A](list: List[A], index: Int) { update: A => A }: List[A] / Exception[OutOfBounds] = {
453
471
  list.splitAt(index) match {
454
472
  case (left, Cons(x, right)) =>
@@ -457,69 +475,69 @@ def modifyAt[A](list: List[A], index: Int) { update: A => A }: List[A] / Excepti
457
475
  }
458
476
  }
459
477
 
460
- // Delete the element at given index in the list.
461
- //
462
- // Example:
463
- // ```
464
- // > [1, 2, 3, 4].deleteAt(1)
465
- // [1, 3, 4]
466
- //
467
- // > [1, 2, 3, 4].deleteAt(-1)
468
- // [1, 2, 3, 4]
469
- //
470
- // > [1, 2, 3, 4].deleteAt(10)
471
- // [1, 2, 3, 4]
472
- // ```
473
- //
474
- // O(N)
478
+ /// Delete the element at given index in the list.
479
+ ///
480
+ /// Example:
481
+ /// ```
482
+ /// > [1, 2, 3, 4].deleteAt(1)
483
+ /// [1, 3, 4]
484
+ ///
485
+ /// > [1, 2, 3, 4].deleteAt(-1)
486
+ /// [1, 2, 3, 4]
487
+ ///
488
+ /// > [1, 2, 3, 4].deleteAt(10)
489
+ /// [1, 2, 3, 4]
490
+ /// ```
491
+ ///
492
+ /// O(N)
475
493
  def deleteAt[A](list: List[A], index: Int): List[A] = {
476
494
  val left = list.slice(0, index)
477
495
  val right = list.slice(index + 1, list.size())
478
496
  left.append(right)
479
497
  }
480
498
 
481
- // Add an element at given index in the list.
482
- //
483
- // Examples:
484
- // ```
485
- // > [1, 2, 3].insert(-1, 0)
486
- // [0, 1, 2, 3]
487
- //
488
- // > [1, 2, 3].insert(0, 0)
489
- // [0, 1, 2, 3]
490
- //
491
- // > [1, 2, 3].insert(1, 0)
492
- // [1, 0, 2, 3]
493
- //
494
- // > [1, 2, 3].insert(3, 0)
495
- // [1, 2, 3, 0]
496
- //
497
- // > [1, 2, 3].insert(10, 0)
498
- // [1, 2, 3, 0]
499
- // ```
500
- //
501
- // O(N)
499
+ /// Add an element at given index in the list.
500
+ ///
501
+ /// Examples:
502
+ /// ```
503
+ /// > [1, 2, 3].insert(-1, 0)
504
+ /// [0, 1, 2, 3]
505
+ ///
506
+ /// > [1, 2, 3].insert(0, 0)
507
+ /// [0, 1, 2, 3]
508
+ ///
509
+ /// > [1, 2, 3].insert(1, 0)
510
+ /// [1, 0, 2, 3]
511
+ ///
512
+ /// > [1, 2, 3].insert(3, 0)
513
+ /// [1, 2, 3, 0]
514
+ ///
515
+ /// > [1, 2, 3].insert(10, 0)
516
+ /// [1, 2, 3, 0]
517
+ /// ```
518
+ ///
519
+ /// O(N)
502
520
  def insert[A](list: List[A], index: Int, x: A): List[A] = {
503
521
  val (left, right) = list.splitAt(index)
504
522
  left.append(Cons(x, right))
505
523
  }
506
524
 
507
- // Replace an element at given index in the list.
508
- // Returns the original list when the index is out of bounds.
509
- //
510
- // Examples:
511
- // ```
512
- // > [1, 2, 3].replace(0, 42)
513
- // [42, 2, 3]
514
- //
515
- // > [1, 2, 3].replace(-1, 42)
516
- // [1, 2, 3]
517
- //
518
- // > [1, 2, 3].replace(10, 42)
519
- // [1, 2, 3]
520
- // ```
521
- //
522
- // O(N)
525
+ /// Replace an element at given index in the list.
526
+ /// Returns the original list when the index is out of bounds.
527
+ ///
528
+ /// Examples:
529
+ /// ```
530
+ /// > [1, 2, 3].replace(0, 42)
531
+ /// [42, 2, 3]
532
+ ///
533
+ /// > [1, 2, 3].replace(-1, 42)
534
+ /// [1, 2, 3]
535
+ ///
536
+ /// > [1, 2, 3].replace(10, 42)
537
+ /// [1, 2, 3]
538
+ /// ```
539
+ ///
540
+ /// O(N)
523
541
  def replace[A](list: List[A], index: Int, x: A): List[A] = {
524
542
  if (index < 0 || index >= list.size()) {
525
543
  list
@@ -530,25 +548,25 @@ def replace[A](list: List[A], index: Int, x: A): List[A] = {
530
548
  }
531
549
  }
532
550
 
533
- // Produce a list of pairs from a pair of lists.
534
- // The length of the result is the minimum of lengths of the two lists.
535
- //
536
- // Examples:
537
- // ```
538
- // > zip([1, 2, 3], [100, 200, 300])
539
- // [(1, 100), (2, 200), (3, 300)]
540
- //
541
- // > zip([1, 2, 3], Nil[Int]())
542
- // []
543
- //
544
- // > zip(Nil[Int](), [1, 2, 3])
545
- // []
546
- //
547
- // > zip([1, 2, 3], [42])
548
- // [(1, 42)]
549
- // ```
550
- //
551
- // O(N)
551
+ /// Produce a list of pairs from a pair of lists.
552
+ /// The length of the result is the minimum of lengths of the two lists.
553
+ ///
554
+ /// Examples:
555
+ /// ```
556
+ /// > zip([1, 2, 3], [100, 200, 300])
557
+ /// [(1, 100), (2, 200), (3, 300)]
558
+ ///
559
+ /// > zip([1, 2, 3], Nil[Int]())
560
+ /// []
561
+ ///
562
+ /// > zip(Nil[Int](), [1, 2, 3])
563
+ /// []
564
+ ///
565
+ /// > zip([1, 2, 3], [42])
566
+ /// [(1, 42)]
567
+ /// ```
568
+ ///
569
+ /// O(N)
552
570
  def zip[A, B](left: List[A], right: List[B]): List[(A, B)] = {
553
571
  def go(acc: List[(A, B)], left: List[A], right: List[B]): List[(A, B)] = {
554
572
  (left, right) match {
@@ -562,25 +580,25 @@ def zip[A, B](left: List[A], right: List[B]): List[(A, B)] = {
562
580
  go(Nil(), left, right)
563
581
  }
564
582
 
565
- // Combine two lists with the given function.
566
- // The length of the result is the minimum of lengths of the two lists.
567
- //
568
- // Examples:
569
- // ```
570
- // > zipWith([1, 2, 3], [100, 200, 300]) { (a, b) => a + b }
571
- // [101, 202, 303]
572
- //
573
- // > zipWith([1, 2, 3], Nil[Int]()) { (a, b) => a + b }
574
- // []
575
- //
576
- // > zipWith(Nil[Int](), [1, 2, 3]) { (a, b) => a + b }
577
- // []
578
- //
579
- // > zipWith([1, 2, 3], [42]) { (a, b) => a + b }
580
- // [43]
581
- // ```
582
- //
583
- // O(N)
583
+ /// Combine two lists with the given function.
584
+ /// The length of the result is the minimum of lengths of the two lists.
585
+ ///
586
+ /// Examples:
587
+ /// ```
588
+ /// > zipWith([1, 2, 3], [100, 200, 300]) { (a, b) => a + b }
589
+ /// [101, 202, 303]
590
+ ///
591
+ /// > zipWith([1, 2, 3], Nil[Int]()) { (a, b) => a + b }
592
+ /// []
593
+ ///
594
+ /// > zipWith(Nil[Int](), [1, 2, 3]) { (a, b) => a + b }
595
+ /// []
596
+ ///
597
+ /// > zipWith([1, 2, 3], [42]) { (a, b) => a + b }
598
+ /// [43]
599
+ /// ```
600
+ ///
601
+ /// O(N)
584
602
  def zipWith[A, B, C](left: List[A], right: List[B]) { combine : (A, B) => C }: List[C] = {
585
603
  def go(acc: List[C], left: List[A], right: List[B]): List[C] = {
586
604
  (left, right) match {
@@ -594,15 +612,15 @@ def zipWith[A, B, C](left: List[A], right: List[B]) { combine : (A, B) => C }: L
594
612
  go(Nil(), left, right)
595
613
  }
596
614
 
597
- // Produce a pair of lists from a list of pairs.
598
- //
599
- // Examples:
600
- // ```
601
- // > [(1, 100), (2, 200), (3, 300)].unzip()
602
- // ([1, 2, 3], [100, 200, 300])
603
- // ```
604
- //
605
- // O(N)
615
+ /// Produce a pair of lists from a list of pairs.
616
+ ///
617
+ /// Examples:
618
+ /// ```
619
+ /// > [(1, 100), (2, 200), (3, 300)].unzip()
620
+ /// ([1, 2, 3], [100, 200, 300])
621
+ /// ```
622
+ ///
623
+ /// O(N)
606
624
  def unzip[A, B](pairs: List[(A, B)]): (List[A], List[B]) = {
607
625
  pairs match {
608
626
  case Nil() => (Nil(), Nil())
@@ -612,11 +630,11 @@ def unzip[A, B](pairs: List[(A, B)]): (List[A], List[B]) = {
612
630
  }
613
631
  }
614
632
 
615
- // Partition a given list into two lists.
616
- // The left list contains the elements that satsify the predicate,
617
- // the right list contains the elements that do not.
618
- //
619
- // O(N)
633
+ /// Partition a given list into two lists.
634
+ /// The left list contains the elements that satsify the predicate,
635
+ /// the right list contains the elements that do not.
636
+ ///
637
+ /// O(N)
620
638
  def partition[A](l: List[A]) { pred: A => Bool }: (List[A], List[A]) = {
621
639
  var lefts: List[A] = Nil()
622
640
  var rights: List[A] = Nil()
@@ -631,11 +649,11 @@ def partition[A](l: List[A]) { pred: A => Bool }: (List[A], List[A]) = {
631
649
  (lefts.reverse, rights.reverse)
632
650
  }
633
651
 
634
- // Sort a list using a given comparison function.
635
- //
636
- // Note: this implementation is not stacksafe!
637
- //
638
- // O(N log N)
652
+ /// Sort a list using a given comparison function.
653
+ ///
654
+ /// Note: this implementation is not stacksafe!
655
+ ///
656
+ /// O(N log N)
639
657
  def sortBy[A](l: List[A]) { compare: (A, A) => Bool }: List[A] =
640
658
  l match {
641
659
  case Nil() => Nil()
@@ -649,9 +667,9 @@ def sortBy[A](l: List[A]) { compare: (A, A) => Bool }: List[A] =
649
667
  def sort(l: List[Int]): List[Int] = l.sortBy { (a, b) => a < b }
650
668
  def sort(l: List[Double]): List[Double] = l.sortBy { (a, b) => a < b }
651
669
 
652
- // Check if a list is sorted according to the given comparison function.
653
- //
654
- // O(N)
670
+ /// Check if a list is sorted according to the given comparison function.
671
+ ///
672
+ /// O(N)
655
673
  def isSortedBy[A](list: List[A]) { compare: (A, A) => Bool }: Bool = {
656
674
  def go(list: List[A]): Bool = {
657
675
  list match {