> On Oct 25, 2016, at 10:30 PM, Charlotte Angela Tortorella > <[email protected]> wrote: > >> Not a replacement for the Swift 4 source stability goal. > > Swift 4 doesn't actually have a source stability goal. It has an ABI > stability goal. These are two very different things. ABI is the calling > conventions of the language.
It has both. >From >https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160725/025676.html > ><https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160725/025676.html> "For Swift 4, the primary goals are to deliver on the promise of source stability from 3.0 on, and to provide ABI stability for the standard library." > >> So, a programmer learns what '?:' means the first time she encounters it and >> knows what it does for the rest of her life, can recognize it when she sees >> it in the many other languages which support it, and can take advantage of >> its terseness if she chooses. I don't see any downsides. > > It's still confusing to learn and conveys no meaning by virtue of its > symbols. Sure, everyone learns what something does and then knows how to use > it, that doesn't change that certain things are less intuitive and create a > higher barrier of entry to the language until one can be considered "fluent". Swift is as much a language for professional programmers as it is for learners. The interests of both must be balanced against each other. > >> I don't agree that any of your functions are more readable than "?:" > > A function that explicitly states what is being returned for certain states > of the `Bool` are implicitly more readable than nothing at all. Once you learn what '?:' does, something which is not conceptually difficult by any means, you don't need to be reminded what is being returned. > >> to any significantly greater degree than a `plus()` function would be more >> readable than `+` > > `+` is a familiar mathematical concept and conveys its meaning to the > layperson quite well. `?:` has no such analogue and conveys nothing to the > layperson. '?:' is a familiar concept to anyone who has experience with the C family languages. There are many 'new to Swift' programmers, just as there are many 'new to programming' Swift programmers. > >> `??` is another magic operator, one that has far less prior art than `?:`; >> why not kill that one first? > > Prior art is no guarantor of quality, case in point `?:`. Prior art (specifically, familiarity to programmers from C-family languages) is the explicit reason for many, many "sub-optimal" decisions Swift made, like calling ADTs 'enums' and supporting both 'default' and 'case _' as the catchall case in switch statements. You can do a search through the mailing list archives if you want to see Chris Lattner talk about this, although I certainly won't blame you if you don't want to dig through the archives; it's a pity gmane is dead. > > >> On 26 Oct. 2016, at 4:20 pm, Austin Zheng <[email protected] >> <mailto:[email protected]>> wrote: >> >> >>> On Oct 25, 2016, at 10:13 PM, Charlotte Angela Tortorella >>> <[email protected] <mailto:[email protected]>> >>> wrote: >>> >>> Addressing breaking source code: this is something that an auto migrator >>> could extremely easily be written for. >> >> Auto migrators are: >> - Specific to Xcode, and therefore OS X Swift development using a very >> specific toolchain >> - Less than reliable for large projects >> - Not a replacement for the Swift 4 source stability goal. >> >>> >>> Addressing your first point, `?:` has the advantage of terseness. Your >>> solution requires a lot of code repetition and invariably a programmer will >>> eventually have to deal with `?:` when interacting with literally anyone >>> else's code. >> >> So, a programmer learns what '?:' means the first time she encounters it and >> knows what it does for the rest of her life, can recognize it when she sees >> it in the many other languages which support it, and can take advantage of >> its terseness if she chooses. I don't see any downsides. >> >>> >>> Addressing your second point, `?:` has no function signature. Thus we >>> should be comparing at call-site value. A Bool extension that mentions >>> `true` and `false` in the function signature is far more readable than the >>> magical operator of `?:`. >> >> I don't agree that any of your functions are more readable than "?:", to any >> significantly greater degree than a `plus()` function would be more readable >> than `+`, but that's probably just a matter of taste. `??` is another magic >> operator, one that has far less prior art than `?:`; why not kill that one >> first? >> >>> >>> Addressing your "finally", you've completely missed the argument about >>> removing complexity from the compiler, considering how `?:` requires >>> special handling. >> >> I don't think it's a worthwhile tradeoff. We had a proposal a few months >> back to remove associated type inference, which would have greatly >> simplified the type checker and fixed a number of critical bugs. It was >> rejected due to the impact it would have on developer ergonomics. Compiler >> complexity is not necessarily a more important goal than user experience. >> >>> >>>> On 26 Oct. 2016, at 4:04 pm, Austin Zheng <[email protected] >>>> <mailto:[email protected]>> wrote: >>>> >>>> Strong -1. I don't feel like stylistic concerns alone are a good enough >>>> reason to introduce a change that will undoubtedly break source >>>> compatibility for many, many projects come Swift 4. >>>> >>>> That aside, I don't agree with the arguments that the ternary operator is >>>> confusing. >>>> >>>> 1. If you don't know that it exists, you aren't hampered in writing code. >>>> The most straightforward solution, and a perfectly good one, is to use an >>>> if-else to assign a value to either a `var` or a `let`. >>>> >>>> 2. If someone new to Swift thinks `?` and `:` are confusing, I really >>>> doubt they will react any better to a generic extension method on a type >>>> (which is a primitive in other languages) which takes two "@autoclosure" >>>> higher-order function parameters. >>>> >>>> Finally, if you don't find any of the arguments above confusing, why force >>>> a breaking change by removing ?: instead of just adding the bool >>>> extension, especially given the source stability goals of Swift 4 and >>>> beyond? >>>> >>>> Best, >>>> Austin >>>> >>>>> On Oct 25, 2016, at 9:51 PM, Charlotte Angela Tortorella via >>>>> swift-evolution <[email protected] >>>>> <mailto:[email protected]>> wrote: >>>>> >>>>> Preamble: I've read over the threads that already exist about the ternary >>>>> operator and to be honest they're a complete mess without a single fully >>>>> formed proposal. >>>>> >>>>> Pitch: I'd like to simplify the syntax, compiler complexity and learning >>>>> curve for newcomers when it comes to dealing with the ternary function. >>>>> The best way to do that, in my opinion, is to remove it entirely and add >>>>> a new function with better semantics that takes care of ternary >>>>> operations entirely within the Swift language. >>>>> >>>>> gist: https://gist.github.com/Qata/25a11c21200f1cf8f43ed78e9ffd727c >>>>> <https://gist.github.com/Qata/25a11c21200f1cf8f43ed78e9ffd727c> >>>>> >>>>> Replace the `?:` operator with an in-language function >>>>> >>>>> Proposal: TBD >>>>> Author: [Charlotte Tortorella](https://github.com/qata >>>>> <https://github.com/qata>) >>>>> Editor: [Soroush Khanlou](https://github.com/khanlou >>>>> <https://github.com/khanlou>) >>>>> Review Manager: TBD >>>>> Status: TBD >>>>> >>>>> Introduction >>>>> <https://gist.github.com/Qata/25a11c21200f1cf8f43ed78e9ffd727c#introduction> >>>>> >>>>> The ternary operator in Swift was added early in development, as a >>>>> holdover >>>>> from C. This document is an attempt to provide a clear look at the >>>>> ternary >>>>> operator without the baggage of the languages that came before, and comes >>>>> to the conclusion that we should deprecate and remove the ternary operator >>>>> in favor of an extension to `Bool`. >>>>> >>>>> As a quick refresher, here's what the ternary operator looks like: >>>>> >>>>> let a = 10 >>>>> let b = 20 >>>>> // If a is less than b, sets e to "foo", else sets e to "bar" >>>>> let e = a < b ? "foo" : "bar" >>>>> >>>>> Advantages of The Ternary Operator >>>>> <https://gist.github.com/Qata/25a11c21200f1cf8f43ed78e9ffd727c#advantages-of-the-ternary-operator> >>>>> >>>>> The primary advantage of this operator is its terseness and expressive >>>>> capability. It's shorthand for (e.g.): >>>>> >>>>> let a = 10 >>>>> let b = 20 >>>>> let e: String >>>>> if a < b { >>>>> e = "foo" >>>>> } else { >>>>> e = "bar" >>>>> } >>>>> >>>>> The second advantage of Swift supporting the ternary operator is >>>>> continuity >>>>> with C, and other common languages in the extended C family (C++, >>>>> Objective-C, >>>>> Java, C#, Javascript, etc). People coming to Swift from these other >>>>> languages >>>>> may reasonably expect this operator to exist. That said, there are also >>>>> popular languages which have kept the majority of C operators but dropped >>>>> the >>>>> ternary operator (e.g. >>>>> [Go](https://golang.org/doc/faq#Does_Go_have_a_ternary_form >>>>> <https://golang.org/doc/faq#Does_Go_have_a_ternary_form>) and >>>>> [Rust](https://github.com/rust-lang/rfcs/issues/1362 >>>>> <https://github.com/rust-lang/rfcs/issues/1362>)). >>>>> >>>>> >>>>> Disadvantages of The Ternary Operator >>>>> <https://gist.github.com/Qata/25a11c21200f1cf8f43ed78e9ffd727c#disadvantages-of-the-ternary-operator> >>>>> >>>>> 1. The existence of the ternary operator as a holdover from C is to >>>>> increase >>>>> the familiarity of the Swift language for C family developers, at the >>>>> expense >>>>> of newcomers. Established developers do much better with learning >>>>> concepts >>>>> than newcomers to programming and probably don't need their hands held >>>>> with this carry over of an operator. >>>>> >>>>> 2. The ternary operator adds complexity to the compiler, because it >>>>> requires >>>>> special handling. It is the only operator that requires two components to >>>>> work (both the `?` and the `:`), it uses a character that is excluded from >>>>> being used in other operators (`:`), and it isn't defined in the standard >>>>> library. >>>>> >>>>> 3. The ternary operator's usage of `?` can be confusing >>>>> to new users. Every other instance of `?` is associated with >>>>> `Optional` values. >>>>> >>>>> 4. The ternary operator uses `:`, which is already a heavily overloaded >>>>> symbol in Swift. `:` is used in hash tables, type annotations for >>>>> variables, >>>>> class inheritance, and protocol conformance. >>>>> >>>>> 5. The ternary operator's short length lends it to being abused in the >>>>> nested ternary operator anti-pattern. This is similar to the `++` and >>>>> `--` operators, which were removed in Swift 3. While they worked fine >>>>> and were >>>>> readable enough when used alone, using them multiple times in a single >>>>> expression like `function(a++, ++a)` made them highly unreadable and >>>>> confusing. >>>>> >>>>> 6. This operator is only applicable to a single type, `Bool`. >>>>> >>>>> 7. If the ternary operator weren't in common usage, it would not be >>>>> proposed >>>>> for Swift. Higher clarity can be achieved with common language features >>>>> by >>>>> creating an extension to `Bool`. >>>>> >>>>> 8. The ternary operator was created for and is much more suited to a >>>>> language >>>>> like C, where there were no generics and as such no alternative to an >>>>> unintuitive operator. >>>>> >>>>> 9. Several other modern languages, like Rust and Go discussed earlier, >>>>> have >>>>> eschewed the usage of the ternary operator entirely. Other languages >>>>> that have >>>>> special constructs similar to `?:`, such as `if then else` in Haskell have >>>>> [discussed removing >>>>> it](https://wiki.haskell.org/If-then-else#Is_If-Then-Else_so_important.3F >>>>> <https://wiki.haskell.org/If-then-else#Is_If-Then-Else_so_important.3F>). >>>>> `if then else` is identical to the `?:` operator, >>>>> excepting that it's prefixed by `if`, while `?:` has no prefix. >>>>> >>>>> Example: `if True then 10 else 20` >>>>> >>>>> 10. On a more personal and anecdotal note, the ternary operator gave me >>>>> more >>>>> trouble than any other operator when I was first learning how to program. >>>>> I’ve also spoken to several other people who expressed similar sentiments >>>>> about this operator’s inscrutability. >>>>> >>>>> Proposed Approach >>>>> <https://gist.github.com/Qata/25a11c21200f1cf8f43ed78e9ffd727c#proposed-approach> >>>>> >>>>> We should drop the ternary operator in favor of a new extension to `Bool`. >>>>> There are a few possibilities for the naming of this function. We've >>>>> provided >>>>> four for consideration in this proposal, but are open to other options as >>>>> well. >>>>> This proposal is much more about the concept than the naming of the >>>>> replacement >>>>> function. >>>>> >>>>> extension Bool { >>>>> /// If `self == true`, returns `t`, otherwise, returns `f`. >>>>> func transformed<T>(true t: @autoclosure () -> T, false f: >>>>> @autoclosure () -> T) -> T { >>>>> if self { >>>>> return t() >>>>> } else { >>>>> return f() >>>>> } >>>>> } >>>>> >>>>> func when<T>(true t: @autoclosure () -> T, false f: @autoclosure () >>>>> -> T) -> T { >>>>> ... >>>>> } >>>>> >>>>> func if<T>(true t: @autoclosure () -> T, false f: @autoclosure () -> >>>>> T) -> T { >>>>> ... >>>>> } >>>>> >>>>> func if<T>(then t: @autoclosure () -> T, else f: @autoclosure () -> >>>>> T) -> T { >>>>> ... >>>>> } >>>>> } >>>>> >>>>> Only one of these should be chosen. We're not proposing adding multiple >>>>> functions that achieve the same thing. >>>>> >>>>> Example usage: >>>>> >>>>> let a = 10 >>>>> let b = 20 >>>>> _ = (a < b).transformed(true: "foo", false: "bar") >>>>> _ = (a < b).when(true: "foo", false: "bar") >>>>> _ = (a < b).if(true: "foo", false: "bar") >>>>> _ = (a < b).if(then: "foo", else: "bar") >>>>> >>>>> Impact on existing code >>>>> <https://gist.github.com/Qata/25a11c21200f1cf8f43ed78e9ffd727c#impact-on-existing-code> >>>>> >>>>> This proposal is breaking and would require migration. >>>>> >>>>> Alternatives considered >>>>> <https://gist.github.com/Qata/25a11c21200f1cf8f43ed78e9ffd727c#alternatives-considered> >>>>> >>>>> Simplest alternative: we could leave the ternary operator as is and not >>>>> introduce any new concepts. >>>>> >>>>> It'd also be possible to add an `if then else` Haskell-esque expression. >>>>> This would have the disadvantages of still needing special handling by the >>>>> compiler. Since this proposal's intention is partially to remove compiler >>>>> complexity, this would be counterproductive and would probably confuse new >>>>> users in a similar way to how `?:` does. >>>>> >>>>> _______________________________________________ >>>>> swift-evolution mailing list >>>>> [email protected] <mailto:[email protected]> >>>>> https://lists.swift.org/mailman/listinfo/swift-evolution >>>>> <https://lists.swift.org/mailman/listinfo/swift-evolution> >>>> >>> >> >
_______________________________________________ swift-evolution mailing list [email protected] https://lists.swift.org/mailman/listinfo/swift-evolution
