From adce562dfda6410982f972801a3399afca8becc5 Mon Sep 17 00:00:00 2001 From: Dan Zheng Date: Wed, 27 Mar 2019 18:04:55 -0700 Subject: [PATCH 1/6] Fix typos in SE-0253. --- proposals/0253-callable.md | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/proposals/0253-callable.md b/proposals/0253-callable.md index 9885b568b8..1f5dd46112 100644 --- a/proposals/0253-callable.md +++ b/proposals/0253-callable.md @@ -121,9 +121,8 @@ A call syntax sugar would enable `BoundClosure` instances to be applied like nor ### Nominal types with one primary method -Some nominal types have a "primary method" that performs their main use. For example: calculators *calculate*, parsers *parse*, neural network layers *apply to inputs*, types representing functions *apply to arguments*, etc. +Some nominal types have a "primary method" that performs their main use. For example: -For example: * Calculators *calculate*: `calculator.calculating(query)`. * Parsers *parse*: `parser.parsing(text)`. * Neural network layers *apply to inputs*: `layer.applied(to: input)`. From 945da0c93e5ae1b9051c2d45c3f8c04e7f574477 Mon Sep 17 00:00:00 2001 From: Dan Zheng Date: Wed, 27 Mar 2019 18:10:22 -0700 Subject: [PATCH 2/6] Improve comment formatting, use ASCII quotes. --- proposals/0253-callable.md | 24 +++++++++++++----------- 1 file changed, 13 insertions(+), 11 deletions(-) diff --git a/proposals/0253-callable.md b/proposals/0253-callable.md index 1f5dd46112..f8bf479348 100644 --- a/proposals/0253-callable.md +++ b/proposals/0253-callable.md @@ -130,11 +130,11 @@ Some nominal types have a "primary method" that performs their main use. For exa Types that have a primary method usually call that method frequently. Thus, it may be desirable to sugar applications of the main method with call syntax to reduce noise. -Let’s explore neural network layers and string parsers in detail. +Let's explore neural network layers and string parsers in detail. #### Neural network layers -[Machine learning](https://en.wikipedia.org/wiki/Machine_learning) models often represent a function that contains an internal state called "trainable parameters", and the function takes an input and predicts the output. In code, models are often represented as a data structure that stores trainable parameters, and a method that defines the transformation from an input to an output in terms of these trained parameters. Here’s an example: +[Machine learning](https://en.wikipedia.org/wiki/Machine_learning) models often represent a function that contains an internal state called "trainable parameters", and the function takes an input and predicts the output. In code, models are often represented as a data structure that stores trainable parameters, and a method that defines the transformation from an input to an output in terms of these trained parameters. Here's an example: ```swift struct Perceptron { @@ -325,7 +325,7 @@ When type-checking fails, error messages look like those for function calls. Whe ```swift add1("foo") -// error: cannot invoke ‘add1’ with an argument list of type '(String)' +// error: cannot invoke ‘add1' with an argument list of type '(String)' // note: overloads for 'call' exist with these partially matching parameter lists: (Float), (Int) add1(1, 2, 3) // error: cannot invoke 'add1' with an argument list of type '(Int, Int, Int)' @@ -387,7 +387,7 @@ The proposed feature adds a `call` keyword. Normally, this would require existin To maintain source compatibility, we propose making `call` a contextual keyword: that is, it is a keyword only in declaration contexts and a normal identifier elsewhere (e.g. in expression contexts). This means that `func call` and `call(...)` (apply expressions) continue to parse correctly. -Here’s a comprehensive example of parsing `call` in different contexts: +Here's a comprehensive example of parsing `call` in different contexts: ```swift struct Callable { @@ -451,7 +451,7 @@ struct Adder { This approach represents call-syntax delegate methods as unnamed `func` declarations instead of creating a new `call` declaration kind. -One option is to use `func(...)` without an identifier name. Since the word "call" does not appear, it is less clear that this denotes a call-syntax delegate method. Additionally, it’s not clear how direct references would work: the proposed design of referencing `call` declarations via `foo.call` is clear and consistent with the behavior of `init` declarations. +One option is to use `func(...)` without an identifier name. Since the word "call" does not appear, it is less clear that this denotes a call-syntax delegate method. Additionally, it's not clear how direct references would work: the proposed design of referencing `call` declarations via `foo.call` is clear and consistent with the behavior of `init` declarations. To make unnamed `func(...)` less weird, one option is to add a `call` declaration modifier: `call func(...)`. The word `call` appears in both this option and the proposed design, clearly conveying "call-syntax delegate method". However, declaration modifiers are currently also treated as keywords, so with both approaches, parser changes to ensure source compatibility are necessary. `call func(...)` requires additional parser changes to allow `func` to sometimes not be followed by a name. The authors lean towards `call` declarations for terseness. @@ -495,6 +495,10 @@ Also, we want to support direct references to call-syntax delegate methods via ` struct Adder { var base: Int // Informal rule: all methods with a particular name (e.g. `func call`) are deemed call-syntax delegate methods. + // + // `StringInterpolationProtocol` has a similar informal requirement for + // `func appendInterpolation` methods. + // https://github.com/apple/swift-evolution/blob/master/proposals/0228-fix-expressiblebystringinterpolation.md#proposed-solution func call(_ x: Int) -> Int { return base + x } @@ -503,7 +507,7 @@ struct Adder { We feel this approach is not ideal because: -* A marker type attribute is not particularly meaningful. The call-syntax delegate methods of a type are what make values of that type callable - a type attribute means nothing by itself. In fact, there’s an edge case that needs to be explicitly handled: if a `@staticCallable` type defines no call-syntax delegate methods, an error must be produced. +* A marker type attribute is not particularly meaningful. The call-syntax delegate methods of a type are what make values of that type callable - a type attribute means nothing by itself. In fact, there's an edge case that needs to be explicitly handled: if a `@staticCallable` type defines no call-syntax delegate methods, an error must be produced. * The name for call-syntax delegate methods (e.g. `func call` ) is not first-class in the language, while their call site syntax is. #### Use a `Callable` protocol to represent callable types @@ -513,8 +517,6 @@ We feel this approach is not ideal because: struct Adder: Callable { var base: Int // Informal rule: all methods with a particular name (e.g. `func call`) are deemed call-syntax delegate methods. - // `StringInterpolationProtocol` has a similar informal requirement for `func appendInterpolation` methods. - // https://github.com/apple/swift-evolution/blob/master/proposals/0228-fix-expressiblebystringinterpolation.md#proposed-solution func call(_ x: Int) -> Int { return base + x } @@ -535,13 +537,13 @@ Halide::Var x, y; foo(x, y) = x + y; ``` -This can be achieved via Swift’s subscripts, which can have a getter and a setter. +This can be achieved via Swift's subscripts, which can have a getter and a setter. ```swift foo[x, y] = x + y ``` -Since the proposed `call` declaration syntax is like `subscript` in many ways, it’s in theory possible to allow `get` and `set` in a `call` declaration’s body. +Since the proposed `call` declaration syntax is like `subscript` in many ways, it's in theory possible to allow `get` and `set` in a `call` declaration's body. ```swift call(x: T) -> U { @@ -554,7 +556,7 @@ call(x: T) -> U { } ``` -However, we do not believe `call` should behave like a storage accessor like `subscript` . Instead, `call` ’s appearance should be as close to function calls as possible. Function call expressions today are not assignable because they can't return an l-value reference, so a call to a `call` member should not be assignable either. +However, we do not believe `call` should behave like a storage accessor like `subscript` . Instead, `call`'s appearance should be as close to function calls as possible. Function call expressions today are not assignable because they can't return an l-value reference, so a call to a `call` member should not be assignable either. ### Static `call` members From 5a4c6881f13acef527d6761f5bacaa0a3819621c Mon Sep 17 00:00:00 2001 From: Dan Zheng Date: Wed, 27 Mar 2019 18:15:13 -0700 Subject: [PATCH 3/6] Remove extra whitespace. --- proposals/0253-callable.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/proposals/0253-callable.md b/proposals/0253-callable.md index f8bf479348..d996c1b2b9 100644 --- a/proposals/0253-callable.md +++ b/proposals/0253-callable.md @@ -12,7 +12,7 @@ Note: throughout this document, let "call-syntax" refer to the syntax of applyin This proposal introduces [callables](https://en.wikipedia.org/wiki/Callable_object) to Swift. Callables are values that define function-like behavior and can be applied using function application syntax. -In a nutshell, we propose to introduce a new declaration syntax with the keyword `call` : +In a nutshell, we propose to introduce a new declaration syntax with the keyword `call`: ```swift struct Adder { @@ -333,7 +333,7 @@ add1(1, 2, 3) ### When the type is also `@dynamicCallable` -A type can both have `call` members and be declared with `@dynamicCallable` . When type-checking a call expression, the type checker will first try to resolve the call to a function or initializer call, then a `call` member call, and finally a dynamic call. +A type can both have `call` members and be declared with `@dynamicCallable`. When type-checking a call expression, the type checker will first try to resolve the call to a function or initializer call, then a `call` member call, and finally a dynamic call. ### Direct reference to a `call` member @@ -556,7 +556,7 @@ call(x: T) -> U { } ``` -However, we do not believe `call` should behave like a storage accessor like `subscript` . Instead, `call`'s appearance should be as close to function calls as possible. Function call expressions today are not assignable because they can't return an l-value reference, so a call to a `call` member should not be assignable either. +However, we do not believe `call` should behave like a storage accessor like `subscript`. Instead, `call`'s appearance should be as close to function calls as possible. Function call expressions today are not assignable because they can't return an l-value reference, so a call to a `call` member should not be assignable either. ### Static `call` members From 5fc86c8a0323151487d6effe4eb5d43471d39432 Mon Sep 17 00:00:00 2001 From: Dan Zheng Date: Wed, 27 Mar 2019 18:16:11 -0700 Subject: [PATCH 4/6] Use ASCII ellipsis. --- proposals/0253-callable.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/proposals/0253-callable.md b/proposals/0253-callable.md index d996c1b2b9..5bace45c49 100644 --- a/proposals/0253-callable.md +++ b/proposals/0253-callable.md @@ -216,7 +216,7 @@ call(_ input: String) throws -> Output { ``` ```swift -let sexpParser: Parser = … +let sexpParser: Parser = ... // Callable syntax. let sexp = sexpParser("(+ 1 2)") ``` @@ -445,7 +445,7 @@ struct Adder { } // Option: `call` declaration modifier on unnamed `func` declarations. // Makes unnamed `func` less weird and clearly states "call". - call func(_ x: Int) -> Int { … } + call func(_ x: Int) -> Int { ... } } ``` From c627c13b09f20bb2bb1181ae872386f2775a8308 Mon Sep 17 00:00:00 2001 From: Dan Zheng Date: Wed, 27 Mar 2019 19:40:05 -0700 Subject: [PATCH 5/6] Abbreviate implementation link. --- proposals/0253-callable.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/proposals/0253-callable.md b/proposals/0253-callable.md index 5bace45c49..44c6f4f60f 100644 --- a/proposals/0253-callable.md +++ b/proposals/0253-callable.md @@ -4,7 +4,7 @@ * Authors: [Richard Wei](https://github.com/rxwei), [Dan Zheng](https://github.com/dan-zheng) * Review Manager: [Chris Lattner](https://github.com/lattner) * Status: **Active review (March 27 - April 5, 2019)** -* Implementation: https://github.com/apple/swift/pull/23517 +* Implementation: [apple/swift#23517](https://github.com/apple/swift/pull/23517) ## Introduction From 71f5ed7e783bd3f9e9b43c6647112e316c020eb5 Mon Sep 17 00:00:00 2001 From: Richard Wei Date: Wed, 27 Mar 2019 19:43:08 -0700 Subject: [PATCH 6/6] Use ASCII quotes. Co-Authored-By: dan-zheng --- proposals/0253-callable.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/proposals/0253-callable.md b/proposals/0253-callable.md index 44c6f4f60f..28d081ea6e 100644 --- a/proposals/0253-callable.md +++ b/proposals/0253-callable.md @@ -325,7 +325,7 @@ When type-checking fails, error messages look like those for function calls. Whe ```swift add1("foo") -// error: cannot invoke ‘add1' with an argument list of type '(String)' +// error: cannot invoke 'add1' with an argument list of type '(String)' // note: overloads for 'call' exist with these partially matching parameter lists: (Float), (Int) add1(1, 2, 3) // error: cannot invoke 'add1' with an argument list of type '(Int, Int, Int)'