Skip to content

Instantly share code, notes, and snippets.

@mattt
Last active April 21, 2023 17:14
Show Gist options
  • Star 89 You must be signed in to star a gist
  • Fork 5 You must be signed in to fork a gist
  • Save mattt/f457625af116721ffb57 to your computer and use it in GitHub Desktop.
Save mattt/f457625af116721ffb57 to your computer and use it in GitHub Desktop.
// See: https://devforums.apple.com/message/1000934#1000934
import Foundation
// Logic
operator prefix ¬ {}
@prefix func ¬ (value: Bool) -> Bool {
return !value
}
operator infix ∧ { associativity left precedence 120 }
func ∧ (left: Bool, right: Bool) -> Bool {
return left && right
}
operator infix ∨ { associativity left precedence 110 }
func ∨ (left: Bool, right: Bool) -> Bool {
return left || right
}
operator infix ⊻ { associativity left precedence 140 }
func ⊻ (left: Bool, right: Bool) -> Bool {
return left ^ right
}
operator infix ⊼ { associativity left precedence 120 }
func ⊼ (left: Bool, right: Bool) -> Bool {
return ¬(left ∧ right)
}
operator infix ⊽ { associativity left precedence 110 }
func ⊽ (left: Bool, right: Bool) -> Bool {
return ¬(left ∨ right)
}
operator prefix ⊦ {}
@prefix func ⊦ (condition: @auto_closure () -> Bool) {
assert(condition, "Assertion Failed")
}
// Math
operator infix × { associativity left precedence 150 }
func × (left: Double, right: Double) -> Double {
return left * right
}
operator infix ÷ { associativity left precedence 150 }
func ÷ (left: Double, right: Double) -> Double {
return left / right
}
operator infix ∕ { associativity left precedence 150 }
func ∕ (left: Double, right: Double) -> Double {
return left / right
}
operator prefix √ {}
@prefix func √ (number: Double) -> Double {
return sqrt(number)
}
operator prefix ∛ {}
@prefix func ∛ (number: Double) -> Double {
return cbrt(number)
}
operator infix ± { associativity left precedence 140 }
func ± (left: Double, right: Double) -> (Double, Double) {
return (left + right, left - right)
}
operator prefix ± {}
@prefix func ± (value: Double) -> (Double, Double) {
return 0 ± value
}
operator infix ∓ { associativity left precedence 140 }
func ∓ (left: Double, right: Double) -> (Double, Double) {
return (left - right, left + right)
}
operator prefix ∓ {}
@prefix func ∓ (value: Double) -> (Double, Double) {
return 0 ∓ value
}
operator infix ∣ { associativity left precedence 150 }
func ∣ (left: Int, right: Int) -> Bool {
return left % right == 0
}
operator infix ∤ { associativity left }
func ∤ (left: Int, right: Int) -> Bool {
return ¬(left ∣ right)
}
// Sets
operator infix ∈ { associativity left }
func ∈<T: Equatable> (left: T, right: Array<T>) -> Bool {
let filtered = right.filter {$0 == left}
return filtered.count > 0
}
operator infix ∉ { associativity left }
func ∉<T: Equatable> (left: T, right: Array<T>) -> Bool {
return ¬(left ∈ right)
}
operator infix ∋ { associativity left }
func ∈<T: Equatable> (left: Array<T>, right: T) -> Bool {
return right ∈ left
}
operator infix ∌ { associativity left }
func ∌<T: Equatable> (left: Array<T>, right: T) -> Bool {
return right ∉ left
}
operator infix ∩ { associativity left }
func ∩<T: Equatable> (left: Array<T>, right: Array<T>) -> Array<T> {
var intersection: Array<T> = []
for value in left {
if value ∈ right {
intersection.append(value)
}
}
return intersection
}
operator infix ∪ { associativity left }
func ∪<T: Equatable> (left: Array<T>, right: Array<T>) -> Array<T> {
var union: Array<T> = left
for value in right {
if ¬(value ∈ left) {
union.append(value)
}
}
return union
}
operator infix ⊂ { associativity left }
func ⊂<T: Equatable> (left: Array<T>, right: Array<T>) -> Bool {
for value in left {
if ¬(value ∈ right) {
return false
}
}
return true
}
operator infix ⊆ { associativity left }
func ⊆<T: Equatable> (left: Array<T>, right: Array<T>) -> Bool {
return left == right || (left ⊂ right)
}
operator infix ⊊ { associativity left }
func ⊊<T: Equatable> (left: Array<T>, right: Array<T>) -> Bool {
return left ⊂ right
}
operator infix ⊄ { associativity left }
func ⊄<T: Equatable> (left: Array<T>, right: Array<T>) -> Bool {
return ¬(left ⊂ right)
}
operator infix ⊃ { associativity left }
func ⊃<T: Equatable> (left: Array<T>, right: Array<T>) -> Bool {
return right ⊂ left
}
operator infix ⊇ { associativity left }
func ⊇<T: Equatable> (left: Array<T>, right: Array<T>) -> Bool {
return right ⊆ left
}
operator infix ⊋ { associativity left }
func ⊋<T: Equatable> (left: Array<T>, right: Array<T>) -> Bool {
return left ⊃ right
}
// Sequences
operator prefix ∑ {}
@prefix func ∑ (values: Array<Double>) -> Double {
return reduce(values, 0.0, +)
}
operator prefix ∏ {}
@prefix func ∏ (values: Array<Double>) -> Double {
return reduce(values, 1.0, *)
}
operator infix ⋅ {}
func ⋅ (left: Array<Double>, right: Array<Double>) -> Double? {
if left.count != right.count {
return nil
}
var product: Array<Double> = []
for (index, _) in enumerate(left) {
let (a, b) = (left[index], right[index])
product.append(a * b)
}
return ∑product
}
// Comparison
operator infix ⩵ { associativity left }
func ⩵<T: Equatable> (left: T, right: T) -> Bool {
return left == right
}
//operator infix ≤ { associativity left }
//func ≤<T: Equatable> (left: T, right: T) -> Bool {
// return left < right || left == right
//}
//operator infix ≥ { associativity left }
//func ≥<T: Equatable> (left: T, right: T) -> Bool {
// return left > right || left == right
//}
//operator infix ≬ { associativity left }
//func ≬<T: Equatable> (left: T, right: (T, T)) -> Bool {
// return left > right.0 && left < right.1
//}
@andymatuschak
Copy link

Cute, @mattt. :)

@smile0210
Copy link

Nice!

@ochococo
Copy link

ochococo commented Jul 9, 2014

Awesome!

@marzapower
Copy link

The "V" function should return "a || b" and not "a && b".

@beccadax
Copy link

I'm not sure if this is intentional, but your logic operators don't short-circuit the way the originals do. If that's a mistake, take a look at @auto_closure to see how to fix this.

@PopFlamingo
Copy link

Wow ! Awesome ! Thank you :)

@lonelytango
Copy link

wow...

@staypufd
Copy link

Very nice!

@xuvw
Copy link

xuvw commented Oct 28, 2014

Awesome!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment