On Mon, Jan 15, 2018 at 4:24 PM, Nevin Brackett-Rozinsky via swift-evolution <firstname.lastname@example.org> wrote:
> Currently, the FloatingPoint protocol does not conform to > ExpressibleByFloatLiteral, whereas BinaryFloatingPoint does. > > The only explanation I can find for this is a brief comment from Steve > Canon > <https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20160425/015691.html> > during the review of SE-0067 (Enhanced Floating Point Protocols) > <https://github.com/apple/swift-evolution/blob/master/proposals/0067-floating-point-protocols.md> > : > > > On Mon, Apr 25, 2016 at 1:32 PM, Stephen Canon via swift-evolution >> <swift-evolution at swift.org> wrote: >> >> On Apr 23, 2016, at 8:53 PM, Brent Royal-Gordon via swift-evolution >>> <swift-evolution at swift.org> wrote: >>> >>> Any reason why FloatLiteralConvertible isn't on FloatingPoint? >> >> >> It doesn’t make sense for non-radix-2 types; you would change bases >> multiple times. > > > > I don’t have Steve’s level of floating-point expertise, but from a > conceptual standpoint Swift protocols encapsulate semantics and, unless I > am quite mistaken, semantically a floating-point number *can* be expressed > as a floating-point literal. > > So, what exactly is the problem preventing such a conformance, and what > would be required to fix it? Do we need to revamp how numeric literals are > handled, eg. to allow arbitrary-precision integers and base-agnostic floats? > Note that there are no types that ship with Swift itself that conform to FloatingPoint but not BinaryFloatingPoint (Foundation.Decimal does not conform to FloatingPoint, and cannot do so without some major backwards-incompatible surgery because of how it handles subnormals, infinity, NaN, and a host of other issues), so this discussion does not affect most (any?) end users. The name ExpressibleByFloatLiteral is kind of a misnomer. To conform, a type must be able to convert a value from some other type that conforms to _ExpressibleByBuiltinFloatLiteral, which is to say a _binary_ floating-point type. If you create a Decimal type, it *could try to conform* to ExpressibleByFloatLiteral, but given `var x: Double = 0.1`, the value would actually be something like 0.10000000000000001, not exactly 0.1, because it'd be the decimal approximation of a _binary_ approximation to the literal. This is what Steve means by "you would change bases multiple times," and the result is unintuitive. The alternative is to try to convert to a decimal value via the _string representation_ of the _binary approximation_ to the literal, which would let you recover `0.1` but lose all information as to significant digits in the original literal (i.e., "0.1" vs. "0.100"), an important piece of information for Decimal types. In other words, given the actual design of ExpressibleByFloatLiteral, it doesn't entirely make sense for non-binary floating-point types to conform. Yes, we can try to perform major surgery on the floating-point literal protocol, or add another one, so that it's possible for non-binary types to conform, and there have been proposals on this list along those lines. It would appear to me that any such design would necessarily be more complex and possibly slower than the existing design; at its simplest, it could involve representing the literal as a string, which almost all types, whether Decimal or BigInt, would expected to be able to parse anyway. But that's a much larger discussion for another day. The answer to your question as to why `FloatingPoint` does not refine `ExpressibleByFloatLiteral` is as shown above; tl;dr: it doesn't make sense to do so.
_______________________________________________ swift-evolution mailing list email@example.com https://lists.swift.org/mailman/listinfo/swift-evolution