// RUN: %target-run-simple-swift | %FileCheck %s // REQUIRES: executable_test enum Either { case first(T) case second(U) } @_functionBuilder struct TupleBuilder { static func buildBlock(_ t1: T1, _ t2: T2) -> (T1, T2) { return (t1, t2) } static func buildBlock(_ t1: T1, _ t2: T2, _ t3: T3) -> (T1, T2, T3) { return (t1, t2, t3) } static func buildBlock(_ t1: T1, _ t2: T2, _ t3: T3, _ t4: T4) -> (T1, T2, T3, T4) { return (t1, t2, t3, t4) } static func buildBlock( _ t1: T1, _ t2: T2, _ t3: T3, _ t4: T4, _ t5: T5 ) -> (T1, T2, T3, T4, T5) { return (t1, t2, t3, t4, t5) } static func buildDo(_ value: T) -> T { return value } static func buildIf(_ value: T?) -> T? { return value } static func buildEither(first value: T) -> Either { return .first(value) } static func buildEither(second value: U) -> Either { return .second(value) } } func tuplify(_ cond: Bool, @TupleBuilder body: (Bool) -> T) { print(body(cond)) } // CHECK: (17, 3.14159, "Hello, DSL", (["nested", "do"], 6), Optional((2.71828, ["if", "stmt"]))) let name = "dsl" tuplify(true) { 17 3.14159 "Hello, \(name.map { $0.uppercased() }.joined())" do { ["nested", "do"] 1 + 2 + 3 } if $0 { 2.71828 ["if", "stmt"] } } // CHECK: ("Empty optional", nil) tuplify(false) { "Empty optional" if $0 { 2.71828 ["if", "stmt"] } } // CHECK: ("chain0", main.Either<(Swift.String, Swift.Double), (Swift.Double, Swift.String)>.second(2.8, "capable")) tuplify(false) { "chain0" if $0 { "marginal" 2.9 } else { 2.8 "capable" } } // CHECK: ("chain1", nil) tuplify(false) { "chain1" if $0 { "marginal" 2.9 } else if $0 { 2.8 "capable" } } // CHECK: ("chain2", Optional(main.Either<(Swift.String, Swift.Double), (Swift.Double, Swift.String)>.first("marginal", 2.9))) tuplify(true) { "chain2" if $0 { "marginal" 2.9 } else if $0 { 2.8 "capable" } } // CHECK: ("chain3", main.Either, main.Either<(Swift.Double, Swift.Double), (Swift.String, Swift.String)>>.first(main.Either<(Swift.String, Swift.Double), (Swift.Double, Swift.String)>.first("marginal", 2.9))) tuplify(true) { "chain3" if $0 { "marginal" 2.9 } else if $0 { 2.8 "capable" } else if $0 { 2.8 1.0 } else { "wild" "broken" } } // CHECK: ("chain4", main.Either, main.Either<(Swift.String, Swift.Int), (Swift.String, Swift.Int)>>, main.Either, (Swift.String, Swift.Int)>>.first tuplify(true) { "chain4" if $0 { "0" 0 } else if $0 { "1" 1 } else if $0 { "2" 2 } else if $0 { "3" 3 } else if $0 { "4" 4 } else if $0 { "5" 5 } else { "6" 6 } } // CHECK: ("getterBuilder", 0, 4, 12) @TupleBuilder var globalBuilder: (String, Int, Int, Int) { "getterBuilder" 0 4 12 } print(globalBuilder) // CHECK: ("funcBuilder", 13, 45.0) @TupleBuilder func funcBuilder(d: Double) -> (String, Int, Double) { "funcBuilder" 13 d } print(funcBuilder(d: 45)) struct MemberBuilders { @TupleBuilder func methodBuilder(_ i: Int) -> (String, Int) { "methodBuilder" i } @TupleBuilder static func staticMethodBuilder(_ i: Int) -> (String, Int) { "staticMethodBuilder" i + 14 } @TupleBuilder var propertyBuilder: (String, Int) { "propertyBuilder" 12 } } // CHECK: ("staticMethodBuilder", 27) print(MemberBuilders.staticMethodBuilder(13)) let mbuilders = MemberBuilders() // CHECK: ("methodBuilder", 13) print(mbuilders.methodBuilder(13)) // CHECK: ("propertyBuilder", 12) print(mbuilders.propertyBuilder) struct Tagged { let tag: Tag let entity: Entity } protocol Taggable { } extension Taggable { func tag(_ tag: Tag) -> Tagged { return Tagged(tag: tag, entity: self) } } extension Int: Taggable { } extension String: Taggable { } extension Double: Taggable { } @_functionBuilder struct TaggedBuilder { static func buildBlock() -> () { } static func buildBlock(_ t1: Tagged) -> Tagged { return t1 } static func buildBlock(_ t1: Tagged, _ t2: Tagged) -> (Tagged, Tagged) { return (t1, t2) } static func buildBlock(_ t1: Tagged, _ t2: Tagged, _ t3: Tagged) -> (Tagged, Tagged, Tagged) { return (t1, t2, t3) } static func buildBlock(_ t1: Tagged, _ t2: Tagged, _ t3: Tagged, _ t4: Tagged) -> (Tagged, Tagged, Tagged, Tagged) { return (t1, t2, t3, t4) } static func buildBlock( _ t1: Tagged, _ t2: Tagged, _ t3: Tagged, _ t4: Tagged, _ t5: Tagged ) -> (Tagged, Tagged, Tagged, Tagged, Tagged) { return (t1, t2, t3, t4, t5) } static func buildIf(_ value: Tagged?) -> Tagged? { return value } } enum Color { case red, green, blue } func acceptColorTagged(@TaggedBuilder body: () -> Result) { print(body()) } struct TagAccepter { static func acceptTagged(@TaggedBuilder body: () -> Result) { print(body()) } } func testAcceptColorTagged(b: Bool, i: Int, s: String, d: Double) { // CHECK: Tagged< acceptColorTagged { i.tag(.red) s.tag(.green) d.tag(.blue) } // CHECK: Tagged< TagAccepter.acceptTagged { i.tag(.red) s.tag(.green) d.tag(.blue) } // CHECK: Tagged< TagAccepter.acceptTagged { () -> Tagged in if b { return i.tag(Color.green) } else { return i.tag(Color.blue) } } } testAcceptColorTagged(b: true, i: 17, s: "Hello", d: 3.14159)