Merge pull request #400 from asarhaddon/improve-mal-impl-macro-no-meta
[jackhill/mal.git] / swift / types_enum.swift
1 //******************************************************************************
2 // MAL - types, implemented as a Swift "enum".
3 //******************************************************************************
4
5 import Foundation
6
7 // ===== Types / Constants / Variables =====
8
9 typealias MalProtocol = protocol<Equatable, CustomStringConvertible, Hashable>
10
11 typealias MalIntType = Int64
12 typealias MalFloatType = Double
13 typealias MalSymbolType = String
14 typealias MalKeywordType = String
15 typealias MalStringType = String
16 typealias MalVectorType = ArraySlice<MalVal>
17 typealias MalHashType = Dictionary<MalVal, MalVal>
18
19 typealias MalInteger = MalIntType
20 typealias MalFloat = MalFloatType
21 typealias MalSymbol = MalSymbolType
22 typealias MalKeyword = MalKeywordType
23 typealias MalString = MalStringType
24
25 private let kUnknown = MalVal.TypeUnknown
26 private let kNil = MalVal.TypeNil
27 private let kTrue = MalVal.TypeTrue
28 private let kFalse = MalVal.TypeFalse
29 private let kComment = MalVal.TypeComment
30
31 // ==================== MalSequence ====================
32
33 class MalSequence : MalProtocol, SequenceType {
34 init() {
35 self.count = 0
36 self.isEmpty = true
37 }
38 init(_ seq: MalSequence) {
39 self.count = seq.count
40 self.isEmpty = seq.isEmpty
41 }
42 init(_ count: MalIntType) {
43 self.count = count
44 self.isEmpty = self.count == 0
45 }
46
47 // CustomStringConvertible
48 //
49 var description: String { die() }
50
51 // Hashable
52 //
53 var hashValue: Int { die() }
54
55 // SequenceType
56 //
57 func generate() -> MalVectorType.Generator { die() }
58
59 // MalSequence
60 //
61 let count: MalIntType
62 let isEmpty: Bool
63
64 func first() -> MalVal { die() }
65 func last() -> MalVal { die() }
66 func rest() -> MalVal { die() }
67 func nth(n: MalIntType) throws -> MalVal { die() }
68 func range_from(from: MalIntType, to: MalIntType) -> MalVal { die() }
69 func cons(element: MalVal) -> MalVal { die() }
70 func concat(seq: MalSequence) throws -> MalVal { die() }
71 func conj(seq: MalSequence) throws -> MalVal { die() }
72 func map<U>(@noescape transform: (MalVal) -> U) -> ArraySlice<U> { die() }
73 func reduce<U>(initial: U, @noescape combine: (U, MalVal) -> U) -> U { die() }
74 }
75
76 // Equatable
77 //
78 func ==(left: MalSequence, right: MalSequence) -> Bool {
79 if left.count != right.count { return false }
80 var left_gen = left.generate()
81 var right_gen = right.generate()
82 while true {
83 if let left = left_gen.next(), right = right_gen.next() {
84 if left != right {
85 return false
86 }
87 } else {
88 break
89 }
90 }
91 return true
92 }
93
94 // ==================== MalList ====================
95
96 final class MalList : MalSequence {
97 override convenience init() {
98 self.init(MalVectorType())
99 }
100 init(_ other: MalList, _ meta: MalVal?) {
101 self._slice = other._slice
102 self._meta = meta
103 super.init(other)
104 }
105 override convenience init(_ seq: MalSequence) {
106 if let list = seq as? MalList { self.init(list._slice) }
107 else
108 if let vector = seq as? MalVector { self.init(vector._slice) }
109 else
110 { self.init(seq.reduce(MalVectorType()){ var s = $0; s.append($1); return s }) }
111 }
112 init(_ slice: MalVectorType) {
113 self._slice = slice
114 self._meta = nil
115 super.init(MalIntType(self._slice.count))
116 }
117 convenience init(_ array: Array<MalVal>) {
118 self.init(array[0..<array.count])
119 }
120 convenience init<T: SequenceType where T.Generator.Element == MalVal>(_ collection: T) {
121 self.init(collection.reduce(MalVectorType()){ var s = $0; s.append($1); return s })
122 }
123
124 // CustomStringConvertible
125 //
126 override var description: String { return "(" + self.map { pr_str($0) }.joinWithSeparator(" ") + ")" }
127
128 // Hashable
129 //
130 override var hashValue: Int { return description.hashValue }
131
132 // SequenceType
133 //
134 override func generate() -> MalVectorType.Generator { return self._slice.generate() }
135
136 // MalSequence
137 //
138 override func first() -> MalVal { return isEmpty ? make_nil() : try! nth(0) }
139 override func last() -> MalVal { return try! nth(count - 1) }
140 override func rest() -> MalVal { return range_from(MalIntType(1), to: MalIntType(count)) }
141 override func nth(n: MalIntType) throws -> MalVal { guard n < count else { try throw_error("index (\(n)) out of range (\(count))") }; return self._slice[self._slice.startIndex.advancedBy(Int(n))] }
142 override func range_from(from: MalIntType, to: MalIntType) -> MalVal {
143 return from <= to && to <= count
144 ? make_list(self._slice[self._slice.startIndex.advancedBy(Int(from))..<self._slice.startIndex.advancedBy(Int(to))])
145 : make_list()
146 }
147 override func cons(element: MalVal) -> MalVal {
148 var result = self._slice
149 result.insert(element, atIndex: result.startIndex)
150 return make_list(result)
151 }
152 override func concat(seq: MalSequence) throws -> MalVal {
153 var result = self._slice
154 if let list = as_listQ(seq) {
155 result.appendContentsOf(list._slice)
156 } else if let vector = as_vectorQ(seq) {
157 result.appendContentsOf(vector._slice)
158 } else {
159 try throw_error("Expected sequence, got \(seq)")
160 }
161 return make_list(result)
162 }
163 override func conj(seq: MalSequence) throws -> MalVal {
164 var result: Array<MalVal>
165 if let list = as_listQ(seq) {
166 result = list._slice.reverse()
167 } else if let vector = as_vectorQ(seq) {
168 result = vector._slice.reverse()
169 } else {
170 try throw_error("Expected sequence, got \(seq)")
171 }
172 result.appendContentsOf(self._slice)
173 return make_list(result)
174 }
175 override func map<U>(@noescape transform: (MalVal) -> U) -> ArraySlice<U> { return ArraySlice<U>(self._slice.map(transform)) }
176 override func reduce<U>(initial: U, @noescape combine: (U, MalVal) -> U) -> U { return self._slice.reduce(initial, combine: combine) }
177
178 // MalList
179 //
180 var meta: MalVal? { return self._meta }
181
182 private let _slice: MalVectorType
183 private let _meta: MalVal?
184 }
185
186 // Equatable
187 //
188 func ==(left: MalList, right: MalList) -> Bool {
189 return (left as MalSequence) == (right as MalSequence)
190 }
191
192 // ==================== MalVector ====================
193
194 final class MalVector : MalSequence {
195 override convenience init() {
196 self.init(MalVectorType())
197 }
198 init(_ other: MalVector, _ meta: MalVal?) {
199 self._slice = other._slice
200 self._meta = meta
201 super.init(other)
202 }
203 override convenience init(_ seq: MalSequence) {
204 if let list = seq as? MalList { self.init(list._slice) }
205 else
206 if let vector = seq as? MalVector { self.init(vector._slice) }
207 else
208 { self.init(seq.reduce(MalVectorType()){ var s = $0; s.append($1); return s }) }
209 }
210 init(_ slice: MalVectorType) {
211 self._slice = slice
212 self._meta = nil
213 super.init(MalIntType(self._slice.count))
214 }
215 convenience init(_ array: Array<MalVal>) {
216 self.init(array[0..<array.count])
217 }
218 convenience init<T: SequenceType where T.Generator.Element == MalVal>(_ collection: T) {
219 self.init(collection.reduce(MalVectorType()){ var s = $0; s.append($1); return s })
220 }
221
222 // CustomStringConvertible
223 //
224 override var description: String { return "[" + self.map { pr_str($0) }.joinWithSeparator(" ") + "]" }
225
226 // Hashable
227 //
228 override var hashValue: Int { return description.hashValue }
229
230 // SequenceType
231 //
232 override func generate() -> MalVectorType.Generator { return self._slice.generate() }
233
234 // MalSequence
235 //
236 override func first() -> MalVal { return isEmpty ? make_nil() : try! nth(0) }
237 override func last() -> MalVal { return try! nth(count - 1) }
238 override func rest() -> MalVal { return range_from(MalIntType(1), to: MalIntType(count)) }
239 override func nth(n: MalIntType) throws -> MalVal { guard n < count else { try throw_error("index (\(n)) out of range (\(count))") }; return self._slice[self._slice.startIndex.advancedBy(Int(n))] }
240 override func range_from(from: MalIntType, to: MalIntType) -> MalVal {
241 return from <= to && to <= count
242 ? make_list(self._slice[self._slice.startIndex.advancedBy(Int(from))..<self._slice.startIndex.advancedBy(Int(to))]) // Yes, make_list
243 : make_list() // Yes, make_list
244 }
245 override func cons(element: MalVal) -> MalVal {
246 var result = self._slice
247 result.insert(element, atIndex: result.startIndex)
248 return make_list(result) // Yes, make_list
249 }
250 override func concat(seq: MalSequence) throws -> MalVal {
251 var result = self._slice
252 if let list = as_listQ(seq) {
253 result.appendContentsOf(list._slice)
254 } else if let vector = as_vectorQ(seq) {
255 result.appendContentsOf(vector._slice)
256 } else {
257 try throw_error("Expected sequence, got \(seq)")
258 }
259 return make_vector(result)
260 }
261 override func conj(seq: MalSequence) throws -> MalVal {
262 var result = self._slice
263 if let list = as_listQ(seq) {
264 result.appendContentsOf(list._slice)
265 } else if let vector = as_vectorQ(seq) {
266 result.appendContentsOf(vector._slice)
267 } else {
268 try throw_error("Expected sequence, got \(seq)")
269 }
270 return make_vector(result)
271 }
272 override func map<U>(@noescape transform: (MalVal) -> U) -> ArraySlice<U> { return ArraySlice<U>(self._slice.map(transform)) }
273 override func reduce<U>(initial: U, @noescape combine: (U, MalVal) -> U) -> U { return self._slice.reduce(initial, combine: combine) }
274
275 // MalVector
276 //
277 var meta: MalVal? { return self._meta }
278
279 private let _slice: MalVectorType
280 private let _meta: MalVal?
281 }
282
283 // Equatable
284 //
285 func ==(left: MalVector, right: MalVector) -> Bool {
286 return (left as MalSequence) == (right as MalSequence)
287 }
288
289 // ==================== MalHashMap ====================
290
291 final class MalHashMap : MalProtocol, SequenceType {
292 convenience init() {
293 self.init(MalHashType())
294 }
295 init(_ other: MalHashMap, _ meta: MalVal?) {
296 self._hash = other._hash
297 self._meta = meta
298 self.count = MalIntType(self._hash.count)
299 self.isEmpty = self._hash.isEmpty
300 }
301 init(_ hash: MalHashType) {
302 self._hash = hash
303 self._meta = nil
304 self.count = MalIntType(self._hash.count)
305 self.isEmpty = self._hash.isEmpty
306 }
307 convenience init(_ seq: MalSequence) {
308 var hash = MalHashType()
309 for var index: MalIntType = 0; index < seq.count; index += 2 {
310 hash[try! seq.nth(index)] = try! seq.nth(index + 1)
311 }
312 self.init(hash)
313 }
314 convenience init<T: CollectionType where T.Generator.Element == MalVal>(_ collection: T) {
315 var hash = MalHashType()
316 for var index = collection.startIndex; index != collection.endIndex; {
317 let key = collection[index++]
318 let value = collection[index++]
319 hash[key] = value
320 }
321 self.init(hash)
322 }
323
324 // CustomStringConvertible
325 //
326 var description: String {
327 var a = [String]()
328 for (k, v) in self._hash {
329 a.append("\(pr_str(k)) \(pr_str(v))")
330 }
331 let s = a.joinWithSeparator(" ")
332 return "{\(s)}"
333 }
334
335 // Hashable
336 //
337 var hashValue: Int { return description.hashValue }
338
339 // SequenceType
340 //
341 func generate() -> MalHashType.Generator { return self._hash.generate() }
342
343 // MalHashMap
344 //
345 let count: MalIntType
346 let isEmpty: Bool
347 var hash: MalHashType { return self._hash }
348 var keys: MalVal { return make_list(self._hash.keys) }
349 var values: MalVal { return make_list(self._hash.values) }
350 var meta: MalVal? { return self._meta }
351
352 func value_for(key: MalVal) -> MalVal? {
353 return self._hash[key]
354 }
355
356 private let _hash: MalHashType
357 private let _meta: MalVal?
358 }
359
360 // Equatable
361 //
362 func ==(left: MalHashMap, right: MalHashMap) -> Bool {
363 if left.count != right.count { return false }
364 var left_gen = left.generate()
365 var right_gen = right.generate()
366 while true {
367 if let left = left_gen.next(), right = right_gen.next() {
368 if left.0 != right.0 || left.1 != right.1 {
369 return false
370 }
371 } else {
372 break
373 }
374 }
375 return true
376 }
377
378 // ==================== MalAtom ====================
379
380 final class MalAtom : MalProtocol {
381 convenience init() {
382 self.init(make_nil())
383 }
384 init(_ other: MalAtom, _ meta: MalVal?) {
385 self._object = other._object
386 self._meta = meta
387 }
388 init(_ object: MalVal) {
389 self._object = object
390 self._meta = nil
391 }
392
393 // CustomStringConvertible
394 //
395 var description: String { return "(atom \(pr_str(self._object)))" }
396
397 // Hashable
398 //
399 var hashValue: Int { return description.hashValue }
400
401 // MalAtom
402 //
403 var object: MalVal { return self._object }
404 var meta: MalVal? { return self._meta }
405
406 func set_object(obj: MalVal) -> MalVal {
407 self._object = obj
408 return obj
409 }
410
411 private var _object: MalVal
412 private let _meta: MalVal?
413 }
414
415 // Equatable
416 //
417 func ==(left: MalAtom, right: MalAtom) -> Bool { return left.object == right.object }
418
419 // ==================== MalFunction ====================
420
421 class MalFunction : MalProtocol {
422 init() {
423 }
424 init(_ other: MalFunction) {
425 }
426
427 // CustomStringConvertible
428 //
429 var description: String { die() }
430
431 // Hashable
432 //
433 var hashValue: Int { die() }
434
435 // MalFunction
436 //
437 func apply(exprs: MalSequence) throws -> MalVal { die() }
438 }
439
440 // Equatable
441 //
442 func ==(left: MalFunction, right: MalFunction) -> Bool { return false }
443
444 // ==================== MalClosure ====================
445
446
447 final class MalClosure : MalFunction {
448 typealias Evaluator = (MalVal, Environment) throws -> MalVal
449 typealias Parameters = (eval: Evaluator, args: MalSequence, body: MalVal, env: Environment)
450
451 override convenience init() {
452 self.init((
453 eval: {(a: MalVal, b: Environment) -> MalVal in make_nil() },
454 args: as_sequence(make_list()),
455 body: make_nil(),
456 env: Environment(outer: nil)
457 ))
458 }
459 init(_ other: MalClosure, _ meta: MalVal?) {
460 self._eval = other._eval
461 self._args = other._args
462 self._body = other._body
463 self._env = other._env
464 self._meta = meta
465 super.init(other)
466 }
467 init(_ p: Parameters) {
468 self._eval = p.eval
469 self._args = p.args
470 self._body = p.body
471 self._env = p.env
472 self._meta = nil
473 super.init()
474 }
475
476 // CustomStringConvertible
477 //
478 override var description: String { return "#<Closure>: (fn* \(self._args.description) \(self._body.description))" }
479
480 // Hashable
481 //
482 override var hashValue: Int { return description.hashValue }
483
484 // MalFunction
485 //
486 override func apply(exprs: MalSequence) throws -> MalVal {
487 let new_env = Environment(outer: self._env)
488 let _ = try new_env.set_bindings(self._args, with_exprs: exprs)
489 // Calling EVAL indirectly via an 'eval' data member is a bit of a hack.
490 // We can't call EVAL directly because this file (types.swift) needs to
491 // be used with many different versions of the main MAL file
492 // (step[0-10]*.swift), and EVAL is declared differently across those
493 // versions. By using this indirection, we avoid that problem.
494 return try self._eval(self._body, new_env)
495 }
496
497 var args: MalSequence { return self._args }
498 var body: MalVal { return self._body }
499 var env: Environment { return self._env }
500 var meta: MalVal? { return self._meta }
501
502 private let _eval: Evaluator!
503 private let _args: MalSequence
504 private let _body: MalVal
505 private let _env: Environment
506 private let _meta: MalVal?
507 }
508
509 // Equatable
510 //
511 func ==(left: MalClosure, right: MalClosure) -> Bool { return false }
512
513 // ==================== MalBuiltin ====================
514
515 final class MalBuiltin : MalFunction {
516 typealias Signature = (MalSequence) throws -> MalVal
517
518 override convenience init() {
519 self.init( {(MalSequence) -> MalVal in make_nil()} )
520 }
521 init(_ other: MalBuiltin, _ meta: MalVal?) {
522 self._fn = other._fn
523 self._meta = meta
524 super.init(other)
525 }
526 init(_ fn: Signature) {
527 self._fn = fn
528 self._meta = nil
529 super.init()
530 }
531
532 // CustomStringConvertible
533 //
534 override var description: String { return "#<Builtin>" }
535
536 // Hashable
537 //
538 override var hashValue: Int { return description.hashValue }
539
540 // MalBuiltin
541 //
542 override func apply(exprs: MalSequence) throws -> MalVal { return try self._fn(exprs) }
543 var meta: MalVal? { return self._meta }
544
545 private let _fn: Signature!
546 private let _meta: MalVal?
547 }
548
549 // Equatable
550 //
551 func ==(left: MalBuiltin, right: MalBuiltin) -> Bool { return false } // Can't compare function references in Swift
552
553 // ==================== MalMacro ====================
554
555 final class MalMacro : MalProtocol {
556 convenience init() {
557 self.init(as_closure(make_closure()))
558 }
559 init(_ other: MalMacro, _ meta: MalVal?) {
560 self._closure = other._closure
561 self._meta = meta
562 }
563 init(_ closure: MalClosure) {
564 self._closure = closure
565 self._meta = nil
566 }
567
568 // CustomStringConvertible
569 //
570 var description: String { return self._closure.description }
571
572 // Hashable
573 //
574 var hashValue: Int { return description.hashValue }
575
576 var args: MalSequence { return self._closure.args }
577 var body: MalVal { return self._closure.body }
578 var env: Environment { return self._closure.env }
579 var meta: MalVal? { return self._meta }
580
581 private let _closure: MalClosure
582 private let _meta: MalVal?
583 }
584
585 // Equatable
586 //
587 func ==(left: MalMacro, right: MalMacro) -> Bool { return false }
588
589 // ==================== MalVal ====================
590
591 enum MalVal : MalProtocol {
592 case TypeUnknown
593 case TypeNil
594 case TypeTrue
595 case TypeFalse
596 case TypeComment
597 case TypeInteger (MalInteger)
598 case TypeFloat (MalFloat)
599 case TypeSymbol (MalSymbol)
600 case TypeKeyword (MalKeyword)
601 case TypeString (MalString)
602 case TypeList (MalList)
603 case TypeVector (MalVector)
604 case TypeHashMap (MalHashMap)
605 case TypeAtom (MalAtom)
606 case TypeClosure (MalClosure)
607 case TypeBuiltin (MalBuiltin)
608 case TypeMacro (MalMacro)
609
610 // CustomStringConvertible
611 //
612 var description: String {
613 switch self {
614 case .TypeUnknown: return "unknown"
615 case .TypeNil: return "nil"
616 case .TypeTrue: return "true"
617 case .TypeFalse: return "false"
618 case .TypeComment: return "comment"
619 case .TypeInteger (let v): return v.description
620 case .TypeFloat (let v): return v.description
621 case .TypeSymbol (let v): return v
622 case .TypeKeyword (let v): return v
623 case .TypeString (let v): return v
624 case .TypeList (let v): return v.description
625 case .TypeVector (let v): return v.description
626 case .TypeHashMap (let v): return v.description
627 case .TypeAtom (let v): return v.description
628 case .TypeClosure (let v): return v.description
629 case .TypeBuiltin (let v): return v.description
630 case .TypeMacro (let v): return v.description
631 }
632 }
633
634 // Hashable
635 //
636 var hashValue: Int {
637 switch self {
638 case .TypeUnknown: return 0
639 case .TypeNil: return 0
640 case .TypeTrue: return 0
641 case .TypeFalse: return 0
642 case .TypeComment: return 0
643 case .TypeInteger (let v): return v.hashValue
644 case .TypeFloat (let v): return v.hashValue
645 case .TypeSymbol (let v): return v.hashValue
646 case .TypeKeyword (let v): return v.hashValue
647 case .TypeString (let v): return v.hashValue
648 case .TypeList (let v): return v.hashValue
649 case .TypeVector (let v): return v.hashValue
650 case .TypeHashMap (let v): return v.hashValue
651 case .TypeAtom (let v): return v.hashValue
652 case .TypeClosure (let v): return v.hashValue
653 case .TypeBuiltin (let v): return v.hashValue
654 case .TypeMacro (let v): return v.hashValue
655 }
656 }
657 }
658
659 // Equatable
660 //
661 func ==(left: MalVal, right: MalVal) -> Bool {
662 switch (left, right) {
663 case (.TypeUnknown, .TypeUnknown): return true
664 case (.TypeNil, .TypeNil): return true
665 case (.TypeTrue, .TypeTrue): return true
666 case (.TypeFalse, .TypeFalse): return true
667 case (.TypeComment, .TypeComment): return false
668 case (.TypeInteger (let vLeft), .TypeInteger (let vRight)): return vLeft == vRight
669 case (.TypeFloat (let vLeft), .TypeFloat (let vRight)): return vLeft == vRight
670 case (.TypeSymbol (let vLeft), .TypeSymbol (let vRight)): return vLeft == vRight
671 case (.TypeKeyword (let vLeft), .TypeKeyword (let vRight)): return vLeft == vRight
672 case (.TypeString (let vLeft), .TypeString (let vRight)): return vLeft == vRight
673 case (.TypeList (let vLeft), .TypeList (let vRight)): return vLeft == vRight
674 case (.TypeVector (let vLeft), .TypeVector (let vRight)): return vLeft == vRight
675 case (.TypeHashMap (let vLeft), .TypeHashMap (let vRight)): return vLeft == vRight
676 case (.TypeAtom (let vLeft), .TypeAtom (let vRight)): return vLeft == vRight
677 case (.TypeClosure (let vLeft), .TypeClosure (let vRight)): return vLeft == vRight
678 case (.TypeBuiltin (let vLeft), .TypeBuiltin (let vRight)): return vLeft == vRight
679 case (.TypeMacro (let vLeft), .TypeMacro (let vRight)): return vLeft == vRight
680
681 case (.TypeList (let vLeft), .TypeVector (let vRight)): return vLeft == vRight
682 case (.TypeVector (let vLeft), .TypeList (let vRight)): return vLeft == vRight
683
684 default: return false
685 }
686 }
687
688 func ==(left: MalList, right: MalVector) -> Bool {
689 if left.count != right.count { return false }
690 var left_gen = left.generate()
691 var right_gen = right.generate()
692 while true {
693 if let left = left_gen.next(), right = right_gen.next() {
694 if left != right {
695 return false
696 }
697 } else {
698 break
699 }
700 }
701 return true
702 }
703
704 func ==(left: MalVector, right: MalList) -> Bool {
705 if left.count != right.count { return false }
706 var left_gen = left.generate()
707 var right_gen = right.generate()
708 while true {
709 if let left = left_gen.next(), right = right_gen.next() {
710 if left != right {
711 return false
712 }
713 } else {
714 break
715 }
716 }
717 return true
718 }
719
720 // ==================== Constructors ====================
721
722 // ----- Default -----
723
724 func make_unknown () -> MalVal { return kUnknown }
725 func make_nil () -> MalVal { return kNil }
726 func make_true () -> MalVal { return kTrue }
727 func make_false () -> MalVal { return kFalse }
728 func make_comment () -> MalVal { return kComment }
729 func make_integer () -> MalVal { return make_integer (MalInteger()) }
730 func make_float () -> MalVal { return make_float (MalFloat()) }
731 func make_symbol () -> MalVal { return make_symbol (MalSymbol()) }
732 func make_keyword () -> MalVal { return make_keyword (MalKeyword()) }
733 func make_string () -> MalVal { return make_string (MalString()) }
734 func make_list () -> MalVal { return make_list (MalList()) }
735 func make_vector () -> MalVal { return make_vector (MalVector()) }
736 func make_hashmap () -> MalVal { return make_hashmap (MalHashMap()) }
737 func make_atom () -> MalVal { return make_atom (MalAtom()) }
738 func make_closure () -> MalVal { return make_closure (MalClosure()) }
739 func make_builtin () -> MalVal { return make_builtin (MalBuiltin()) }
740 func make_macro () -> MalVal { return make_macro (MalMacro()) }
741
742 // ----- Base -----
743
744 func make_integer (v: MalInteger) -> MalVal { return MalVal.TypeInteger(v) }
745 func make_float (v: MalFloat) -> MalVal { return MalVal.TypeFloat(v) }
746 func make_symbol (v: MalSymbol) -> MalVal { return MalVal.TypeSymbol(v) }
747 func make_keyword (v: MalKeyword) -> MalVal { return MalVal.TypeKeyword(v) }
748 func make_string (v: MalString) -> MalVal { return MalVal.TypeString(v) }
749 func make_list (v: MalList) -> MalVal { return MalVal.TypeList(v) }
750 func make_vector (v: MalVector) -> MalVal { return MalVal.TypeVector(v) }
751 func make_hashmap (v: MalHashMap) -> MalVal { return MalVal.TypeHashMap(v) }
752 func make_atom (v: MalAtom) -> MalVal { return MalVal.TypeAtom(v) }
753 func make_closure (v: MalClosure) -> MalVal { return MalVal.TypeClosure(v) }
754 func make_builtin (v: MalBuiltin) -> MalVal { return MalVal.TypeBuiltin(v) }
755 func make_macro (v: MalMacro) -> MalVal { return MalVal.TypeMacro(v) }
756
757 // ----- Parameterized -----
758
759 func make_list (v: MalSequence) -> MalVal { return make_list(MalList(v)) }
760 func make_list (v: MalVectorType) -> MalVal { return make_list(MalList(v)) }
761 func make_list (v: Array<MalVal>) -> MalVal { return make_list(MalList(v)) }
762 func make_list_from (v: MalVal...) -> MalVal { return make_list(MalList(v)) }
763 func make_list<T: SequenceType where T.Generator.Element == MalVal>
764 (v: T) -> MalVal { return make_list(MalList(v)) }
765 func make_vector (v: MalSequence) -> MalVal { return make_vector(MalVector(v)) }
766 func make_vector (v: MalVectorType) -> MalVal { return make_vector(MalVector(v)) }
767 func make_vector (v: Array<MalVal>) -> MalVal { return make_vector(MalVector(v)) }
768 func make_vector_from (v: MalVal...) -> MalVal { return make_vector(MalVector(v)) }
769 func make_vector<T: SequenceType where T.Generator.Element == MalVal>
770 (v: T) -> MalVal { return make_vector(MalVector(v)) }
771 func make_hashmap (v: MalSequence) -> MalVal { return make_hashmap(MalHashMap(v)) }
772 func make_hashmap (v: MalHashType) -> MalVal { return make_hashmap(MalHashMap(v)) }
773 func make_hashmap<T: CollectionType where T.Generator.Element == MalVal>
774 (v: T) -> MalVal { return make_hashmap(MalHashMap(v)) }
775 func make_atom (v: MalVal) -> MalVal { return make_atom(MalAtom(v)) }
776 func make_closure (v: MalClosure.Parameters) -> MalVal { return make_closure(MalClosure(v)) }
777 func make_builtin (v: MalBuiltin.Signature) -> MalVal { return make_builtin(MalBuiltin(v)) }
778 func make_macro (v: MalClosure) -> MalVal { return make_macro(MalMacro(v)) }
779
780 // ==================== Predicates ====================
781
782 // ----- Simple -----
783
784 func is_unknown (v: MalVal) -> Bool { if case .TypeUnknown = v { return true } else { return false } }
785 func is_nil (v: MalVal) -> Bool { if case .TypeNil = v { return true } else { return false } }
786 func is_true (v: MalVal) -> Bool { if case .TypeTrue = v { return true } else { return false } }
787 func is_false (v: MalVal) -> Bool { if case .TypeFalse = v { return true } else { return false } }
788 func is_comment (v: MalVal) -> Bool { if case .TypeComment = v { return true } else { return false } }
789 func is_integer (v: MalVal) -> Bool { if case .TypeInteger = v { return true } else { return false } }
790 func is_float (v: MalVal) -> Bool { if case .TypeFloat = v { return true } else { return false } }
791 func is_symbol (v: MalVal) -> Bool { if case .TypeSymbol = v { return true } else { return false } }
792 func is_keyword (v: MalVal) -> Bool { if case .TypeKeyword = v { return true } else { return false } }
793 func is_string (v: MalVal) -> Bool { if case .TypeString = v { return true } else { return false } }
794 func is_list (v: MalVal) -> Bool { if case .TypeList = v { return true } else { return false } }
795 func is_vector (v: MalVal) -> Bool { if case .TypeVector = v { return true } else { return false } }
796 func is_hashmap (v: MalVal) -> Bool { if case .TypeHashMap = v { return true } else { return false } }
797 func is_atom (v: MalVal) -> Bool { if case .TypeAtom = v { return true } else { return false } }
798 func is_closure (v: MalVal) -> Bool { if case .TypeClosure = v { return true } else { return false } }
799 func is_builtin (v: MalVal) -> Bool { if case .TypeBuiltin = v { return true } else { return false } }
800 func is_macro (v: MalVal) -> Bool { if case .TypeMacro = v { return true } else { return false } }
801
802 // ----- Compound -----
803
804 func is_truthy (v: MalVal) -> Bool { return !is_falsey(v) }
805 func is_falsey (v: MalVal) -> Bool { switch v { case .TypeNil, .TypeFalse: return true; default: return false } }
806 func is_number (v: MalVal) -> Bool { switch v { case .TypeInteger, .TypeFloat: return true; default: return false } }
807 func is_sequence (v: MalVal) -> Bool { switch v { case .TypeList, .TypeVector: return true; default: return false } }
808 func is_function (v: MalVal) -> Bool { switch v { case .TypeClosure, .TypeBuiltin: return true; default: return false } }
809
810 // ==================== Converters/Extractors ====================
811
812 func as_integer (v: MalVal) -> MalInteger { if case .TypeInteger(let w) = v { return w }; die("expected integer, got \(v)") }
813 func as_float (v: MalVal) -> MalFloat { if case .TypeFloat(let w) = v { return w }; die("expected float, got \(v)") }
814 func as_symbol (v: MalVal) -> MalSymbol { if case .TypeSymbol(let w) = v { return w }; die("expected symbol, got \(v)") }
815 func as_keyword (v: MalVal) -> MalKeyword { if case .TypeKeyword(let w) = v { return w }; die("expected keyword, got \(v)") }
816 func as_string (v: MalVal) -> MalString { if case .TypeString(let w) = v { return w }; die("expected string, got \(v)") }
817 func as_list (v: MalVal) -> MalList { if case .TypeList(let w) = v { return w }; die("expected list, got \(v)") }
818 func as_vector (v: MalVal) -> MalVector { if case .TypeVector(let w) = v { return w }; die("expected vector, got \(v)") }
819 func as_hashmap (v: MalVal) -> MalHashMap { if case .TypeHashMap(let w) = v { return w }; die("expected hashmap, got \(v)") }
820 func as_atom (v: MalVal) -> MalAtom { if case .TypeAtom(let w) = v { return w }; die("expected atom, got \(v)") }
821 func as_closure (v: MalVal) -> MalClosure { if case .TypeClosure(let w) = v { return w }; die("expected closure, got \(v)") }
822 func as_builtin (v: MalVal) -> MalBuiltin { if case .TypeBuiltin(let w) = v { return w }; die("expected builtin, got \(v)") }
823 func as_macro (v: MalVal) -> MalMacro { if case .TypeMacro(let w) = v { return w }; die("expected macro, got \(v)") }
824
825 func as_sequence (v: MalVal) -> MalSequence {
826 switch v {
827 case .TypeList(let v): return v
828 case .TypeVector(let v): return v
829 default: die("expected sequence, got \(v)")
830 }
831 }
832 func as_function (v: MalVal) -> MalFunction {
833 switch v {
834 case .TypeClosure(let v): return v
835 case .TypeBuiltin(let v): return v
836 default: die("expected function, got \(v)")
837 }
838 }
839
840 func as_inttype (v: MalVal) -> MalIntType { return as_integer(v) }
841 func as_floattype (v: MalVal) -> MalFloatType { return as_float(v) }
842 func as_stringtype (v: MalVal) -> MalStringType { return as_string(v) }
843
844 func as_inttype (v: MalInteger) -> MalIntType { return v }
845 func as_floattype (v: MalFloat) -> MalFloatType { return v }
846 func as_stringtype (v: MalString) -> MalStringType { return v }
847
848 func as_integerQ (v: MalVal) -> MalInteger? { if case .TypeInteger(let w) = v { return w }; return nil }
849 func as_floatQ (v: MalVal) -> MalFloat? { if case .TypeFloat(let w) = v { return w }; return nil }
850 func as_symbolQ (v: MalVal) -> MalSymbol? { if case .TypeSymbol(let w) = v { return w }; return nil }
851 func as_keywordQ (v: MalVal) -> MalKeyword? { if case .TypeKeyword(let w) = v { return w }; return nil }
852 func as_stringQ (v: MalVal) -> MalString? { if case .TypeString(let w) = v { return w }; return nil }
853 func as_listQ (v: MalVal) -> MalList? { if case .TypeList(let w) = v { return w }; return nil }
854 func as_vectorQ (v: MalVal) -> MalVector? { if case .TypeVector(let w) = v { return w }; return nil }
855 func as_hashmapQ (v: MalVal) -> MalHashMap? { if case .TypeHashMap(let w) = v { return w }; return nil }
856 func as_atomQ (v: MalVal) -> MalAtom? { if case .TypeAtom(let w) = v { return w }; return nil }
857 func as_closureQ (v: MalVal) -> MalClosure? { if case .TypeClosure(let w) = v { return w }; return nil }
858 func as_builtinQ (v: MalVal) -> MalBuiltin? { if case .TypeBuiltin(let w) = v { return w }; return nil }
859 func as_macroQ (v: MalVal) -> MalMacro? { if case .TypeMacro(let w) = v { return w }; return nil }
860
861 func as_listQ (v: MalSequence) -> MalList? { return v as? MalList }
862 func as_vectorQ (v: MalSequence) -> MalVector? { return v as? MalVector }
863
864 func as_sequenceQ (v: MalVal) -> MalSequence? {
865 switch v {
866 case .TypeList(let v): return v
867 case .TypeVector(let v): return v
868 default: return nil
869 }
870 }
871 func as_functionQ (v: MalVal) -> MalFunction? {
872 switch v {
873 case .TypeClosure(let v): return v
874 case .TypeBuiltin(let v): return v
875 default: return nil
876 }
877 }
878
879 func as_inttypeQ (v: MalVal) -> MalIntType? { return as_integerQ(v) }
880 func as_floattypeQ (v: MalVal) -> MalFloatType? { return as_floatQ(v) }
881 func as_stringtypeQ (v: MalVal) -> MalStringType? { return as_stringQ(v) }
882
883 // ==================== Exceptions ====================
884
885 enum MalException: ErrorType, CustomStringConvertible {
886 case None
887 case Message(String)
888 case Object(MalVal)
889
890 var exception: MalVal {
891 switch self {
892 case .None:
893 return make_nil()
894 case .Message(let v):
895 return make_string(v)
896 case .Object(let v):
897 return v
898 }
899 }
900
901 // CustomStringConvertible
902 //
903 var description: String {
904 switch self {
905 case .None:
906 return "NIL Exception"
907 case .Message(let v):
908 return v
909 case .Object(let v):
910 return v.description
911 }
912 }
913 }
914
915 @noreturn
916 func throw_error(v: String) throws { throw MalException.Message(v) }
917
918 @noreturn
919 func throw_error(v: MalVal) throws { throw MalException.Object(v) }
920
921 // ==================== Utilities ====================
922
923 @noreturn private func die(msg: String) {
924 preconditionFailure(msg)
925 }
926
927 @noreturn private func die() {
928 die("Should not get here")
929 }
930
931 func get_meta(v: MalVal) -> MalVal? {
932 switch v {
933 case .TypeUnknown: return nil
934 case .TypeNil: return nil
935 case .TypeTrue: return nil
936 case .TypeFalse: return nil
937 case .TypeComment: return nil
938 case .TypeInteger: return nil
939 case .TypeFloat: return nil
940 case .TypeSymbol: return nil
941 case .TypeKeyword: return nil
942 case .TypeString: return nil
943 case .TypeList (let v): return v.meta
944 case .TypeVector (let v): return v.meta
945 case .TypeHashMap (let v): return v.meta
946 case .TypeAtom (let v): return v.meta
947 case .TypeClosure (let v): return v.meta
948 case .TypeBuiltin (let v): return v.meta
949 case .TypeMacro (let v): return v.meta
950 }
951 }
952
953 func with_meta(obj: MalVal, _ meta: MalVal) -> MalVal {
954 switch obj {
955 case .TypeUnknown: return obj
956 case .TypeNil: return obj
957 case .TypeTrue: return obj
958 case .TypeFalse: return obj
959 case .TypeComment: return obj
960 case .TypeInteger: return obj
961 case .TypeFloat: return obj
962 case .TypeSymbol: return obj
963 case .TypeKeyword: return obj
964 case .TypeString: return obj
965 case .TypeList (let v): return make_list(MalList(v, meta))
966 case .TypeVector (let v): return make_vector(MalVector(v, meta))
967 case .TypeHashMap (let v): return make_hashmap(MalHashMap(v, meta))
968 case .TypeAtom (let v): return make_atom(MalAtom(v, meta))
969 case .TypeClosure (let v): return make_closure(MalClosure(v, meta))
970 case .TypeBuiltin (let v): return make_builtin(MalBuiltin(v, meta))
971 case .TypeMacro (let v): return make_macro(MalMacro(v, meta))
972 }
973 }
974
975 func unescape(s: String) -> String {
976 var index = 0
977 var prev_is_escape = false
978 var str = ""
979 let chars = s.characters
980 for ch in chars {
981 if index == chars.count - 1 { continue }
982 if index++ == 0 { continue }
983 if prev_is_escape {
984 prev_is_escape = false
985 if ch == "n" { str.appendContentsOf("\n") }
986 else if ch == "r" { str.appendContentsOf("\r") }
987 else if ch == "t" { str.appendContentsOf("\t") }
988 else { str.append(ch) }
989 } else if ch == "\\" {
990 prev_is_escape = true
991 } else {
992 str.append(ch)
993 }
994 }
995 return str
996 }
997
998 func escape(s: String) -> String {
999 var str = ""
1000 let chars = s.characters
1001 for ch in chars {
1002 if ch == "\n" { str.appendContentsOf("\\n"); continue }
1003 if ch == "\r" { str.appendContentsOf("\\r"); continue }
1004 if ch == "\t" { str.appendContentsOf("\\t"); continue }
1005 if ch == "\"" || ch == "\\" { str.appendContentsOf("\\") }
1006 str.append(ch)
1007 }
1008 str = "\"" + str + "\""
1009 return str
1010 }