Skip to content

Instantly share code, notes, and snippets.

@marcusrossel
Created April 17, 2018 17:15
Show Gist options
  • Save marcusrossel/954c759c3e234cfcf99375ab55c1b940 to your computer and use it in GitHub Desktop.
Save marcusrossel/954c759c3e234cfcf99375ab55c1b940 to your computer and use it in GitHub Desktop.
/*IN- AND OUTPUT TYPES*********************************************************/
// All methods and initializers are taking an instance of `In` as argument.
// The `PAT` and `PWSR` protocols does not adhere to this.
struct In { }
// All methods are returning an instance of `Out` as return value.
// The `methodReturningSelf` methods and the `PAT` protocol do not adhere to
// this.
struct Out { }
/*STRUCT***********************************************************************/
struct S {
static func staticMethod (in: In) -> Out { return Out() }
mutating func mutatingMethod (in: In) -> Out { return Out() }
func method (in: In) -> Out { return Out() }
init (in: In) { }
}
// Instance of `S`.
var s = S(in: In())
let s0 = S.staticMethod // (In) -> Out
let s1 = S.mutatingMethod // (inout S) -> (In) -> Out
let s2 = S.method // (S) -> (In) -> Out
let s3 = S.init // (In) -> S
let s4 = s.method // (In) -> Out
// let s5 = s.staticMethod
//
// Error: Static member 'staticMethod' cannot be used on instance of type 'S'
// let s6 = s.mutatingMethod
//
// Error: Partial application of 'mutating' method is not allowed
// let s7 = s.init
//
// Error: 'init' is a member of the type; use 'type(of: ...)' to initialize a
// new object of the same dynamic type
/*CLASS************************************************************************/
class C {
static func staticMethod (in: In) -> Out { return Out() }
class func classMethod (in: In) -> Out { return Out() }
func method (in: In) -> Out { return Out() }
init (in: In) { }
}
// Instance of `C`.
var c = C(in: In())
let c0 = C.staticMethod // (In) -> Out
let c1 = C.classMethod // (In) -> Out
let c2 = C.method // (C) -> In -> Out
let c3 = C.init // (In) -> C
let c4 = c.method // (In) -> Out
// let c5 = c.staticMethod
//
// Error: Static member 'staticMethod' cannot be used on instance of type 'C'
// let c6 = c.classMethod
//
// Error: Static member 'classMethod' cannot be used on instance of type 'C'
// let c7 = c.init
//
// Error: 'init' is a member of the type; use 'type(of: ...)' to initialize a
// new object of the same dynamic type
/*ENUM*************************************************************************/
enum E {
static func staticMethod (_ a: In) -> Out { return Out() }
mutating func mutatingMethod (_ a: In) -> Out { return Out() }
func method (_ a: In) -> Out { return Out() }
init (in: In) { self.init(in: `in`) }
}
// Instance of `E`.
var e = E(in: In())
let e0 = E.staticMethod // (In) -> Out
let e1 = E.mutatingMethod // (inout E) -> (In) -> Out
let e2 = E.method // (E) -> (In) -> Out
let e3 = E.init // (In) -> E
let e4 = e.method // (In) -> Out
// let e5 = e.staticMethod
//
// Error: Static member 'staticMethod' cannot be used on instance of type 'E'
// let e6 = e.mutatingMethod
//
// Error: Partial application of 'mutating' method is not allowed
// let e7 = e.init
//
// Error: 'init' is a member of the type; use 'type(of: ...)' to initialize a
// new object of the same dynamic type
/*PROTOCOL WITHOUT ASSOCIATED TYPE OR SELF REQUIREMENT, USING AN EXISTENTIAL***/
protocol P {
static func staticMethod (in: In) -> Out
mutating func mutatingMethod (in: In) -> Out
func methodReturningSelf (in: In) -> Self
func method (in: In) -> Out
init (in: In)
}
// Adds conformance for `S`, to have some instantiatable type conforming to `P`.
extension S: P {
func methodReturningSelf(in: In) -> S { return S(in: In()) }
}
// An existential for `P`.
var p: P = S(in: In())
let p0 = p.methodReturningSelf // (In) -> P
let p1 = p.method // (In) -> Out
// let p2 = P.staticMethod
//
// Error: Static member 'staticMethod' cannot be used on protocol metatype
// 'P.Protocol'
// let p3 = P.mutatingMethod
//
// -> Command failed due to signal: Segmentation fault: 11
// let p4 = P.methodReturningSelf
//
// -> Command failed due to signal: Segmentation fault: 11
// let p5 = P.method
//
// -> Command failed due to signal: Segmentation fault: 11
// let p6 = P.init
//
// Error: Protocol type 'P' cannot be instantiated
// let p7 = p.staticMethod
//
// Error: Static member 'staticMethod' cannot be used on instance of type 'P'
// let p8 = p.mutatingMethod
//
// Error: Partial application of 'mutating' method is not allowed
// let p9 = p.init
//
// Error: Static member 'init' cannot be used on instance of type 'P'
/*PROTOCOL WITHOUT ASSOCIATED TYPE OR SELF REQUIREMENT, USING A CONSTRAINED GENERIC*/
func genericForP<T: P>(t: T) {
// A mutable instance of `T`.
var t = t
let t0 = T.staticMethod // (In) -> Out
let t1 = T.mutatingMethod // (inout T) -> (In) -> Out
let t2 = T.methodReturningSelf // (T) -> (In) -> T
let t3 = T.method // (T) -> (In) -> Out
let t4 = T.init // (In) -> T
let t5 = t.methodReturningSelf // (In) -> T
let t6 = t.method // (In) -> Out
// let t7 = t.staticMethod
//
// Error: Static member 'staticMethod' cannot be used on instance of type 'T'
// let t8 = t.mutatingMethod
//
// Error: Partial application of 'mutating' method is not allowed
// let t9 = t.init
//
// Error: 'init' is a member of the type; use 'type(of: ...)' to initialize a
// new object of the same dynamic type
}
/*PROTOCOL WITH ASSOCIATED TYPE, USING A CONSTRAINED GENERIC*******************/
protocol PAT {
// In- and output types for this protocol.
associatedtype I
associatedtype O
static func staticMethod (in: I) -> O
mutating func mutatingMethod (in: I) -> O
func methodReturningSelf (in: I) -> Self
func method (in: I) -> O
init (in: I)
}
func genericForPAT<U: PAT>(u: U) {
// A mutable instance of `U`.
var u = u
let u0 = U.staticMethod // (U.I) -> U.O
let u1 = U.mutatingMethod // (inout U) -> (U.I) -> U.O
let u2 = U.methodReturningSelf // (U) -> (U.I) -> U
let u3 = U.method // (U) -> (U.I) -> U.O
let u4 = U.init // (U.I) -> U
let u5 = u.methodReturningSelf // (U.I) -> U
let u6 = u.method // (U.I) -> U.O
// let u7 = u.staticMethod
//
// Error: Static member 'staticMethod' cannot be used on instance of type 'U'
// let u8 = u.mutatingMethod
//
// Error: Partial application of 'mutating' method is not allowed
// let u9 = u.init
//
// Error: 'init' is a member of the type; use 'type(of: ...)' to initialize a
// new object of the same dynamic type
}
/*PROTOCOL WITH SELF REQUIREMENT, USING A CONSTRAINED GENERIC******************/
protocol PWSR {
static func staticMethod (in: Self) -> Out
mutating func mutatingMethod (in: Self) -> Out
func methodReturningSelf (in: Self) -> Self
func method (in: Self) -> Out
init (in: Self)
}
func genericForPWSR<V: PWSR>(v: V) {
// A mutable instance of `V`.
var v = v
let v0 = V.staticMethod // (V) -> Out
let v1 = V.mutatingMethod // (inout V) -> (V) -> Out
let v2 = V.methodReturningSelf // (V) -> (V) -> V
let v3 = V.method // (V) -> (V) -> Out
let v4 = V.init // (V) -> V
let v5 = v.methodReturningSelf // (V) -> V
let v6 = v.method // (V) -> Out
// let v7 = v.staticMethod
//
// Error: Static member 'staticMethod' cannot be used on instance of type 'V'
// let v8 = v.mutatingMethod
//
// Error: Partial application of 'mutating' method is not allowed
// let v9 = v.init
//
// Error: 'init' is a member of the type; use 'type(of: ...)' to initialize a
// new object of the same dynamic type
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment