[swift-evolution] [Pitch] Ban the top value in Int/UInt

Guoye Zhang cc941201 at me.com
Tue Oct 18 14:10:15 CDT 2016


> 在 2016年10月18日,14:54,Kevin Nattinger <swift at nattinger.net> 写道:
> 
> Part of the beauty of how optionals are implemented in Swift is that the compiler doesn’t have to do any magic w.r.t. optionals besides a bit of syntactic sugar (`T?` -> `Optional<T>`, `if let x` -> `if let case .some(x)`, auto-boxing when necessary, etc.). 
Swift compiler is already using magic for optional pointers. Invalid address are used for optional pointers. `MemoryLayout<ManagedBuffer<Int, String>???>.size` is still 8.

> - I strongly dislike the idea of special-casing optionals just to save a Byte. 
Not just a byte, it saves half the space in arrays. [Int?] is double the size of [Int].

> - Optionals were presented as explicitly removing the need for such a sentinel value in the first place.
> - There are reasonable cases where such a bit pattern is reasonably necessary to the data (e.g. bit fields, RSSI, IP addresses, etc.) and removing that value would force ugly workarounds and/or moving to a larger int size because of an ill-advised implementation detail.
I agree. Perhaps we just special case Int, and keep UInt intact for bitwise operations?

> - If performance or memory is so critical to your specific use case, use a non-optional and your own sentinel value. It’s likely no less efficient than having the compiler do it that way.
> 
> (more below)
> 
>> On Oct 18, 2016, at 11:17 AM, Guoye Zhang via swift-evolution <swift-evolution at swift.org> wrote:
>> 
>> Currently, Swift Int family and UInt family have compact representations that utilize all available values, which is inherited from C. However, it is horribly inefficient to implement optional integers. It takes double the space to store [Int?] than to store [Int] because of alignment.
>> 
>> I propose to ban the top value in Int/UInt which is 0xFFFF... in hex. Int family would lose its smallest value, and UInt family would lose its largest value. Top value is reserved for nil in optionals. An additional benefit is that negating an Int would never crash.
>> 
>> Interacting with C/Obj-C is a major concern, but since we are already importing some of the unsigned integers as Int which loses half the values,
> 
> I’d argue those imports are bugs and should be fixed to the correct signedness.

It is for indexing Swift array easier.
> 
>> one value is not such big a drawback.
> 
> Unless you happen to need all $width bits.
> 
>> Alternatively, we could leave current behavior as CInt/CUInt. Converting them to the new Int?/UInt? doesn't generate any instructions since the invalid value already represents nil.
> 
> Trying to convert an invalid value like that crashes in most of Swift.

CInt to Optional<Int> would not crash because invalid value becomes nil.
> 
>> 
>> With optional integers improved, we could implement safe arithmetic efficiently, or even revisit lenient subscript proposals,
> 
> I don’t see how losing a particular value has any effect on either of those, but it’s possible there’s some theory or implementation detail I’m not aware of.

Unaligned memory access would be a huge performance hit.
> 
>> but they are not in the scope of this pitch. Float/Double optionals could also be improved with the similar idea. (Isn't signaling nan the same as nil) Nested optionals such as "Int??" are still bloated, but I don't think they are widely used.
>> 
>> So what do you think? Can we break C compatibility a bit for better Swift types?
> 
> We can, and do. C.f. structs, non- at objc classes, and enums not RawRepresentable with a C-compatible entity. If anything, this breaks compatibility with the rest of Swift.

I don't want that, either.
> 
>> 
>> - Guoye
>> _______________________________________________
>> swift-evolution mailing list
>> swift-evolution at swift.org
>> https://lists.swift.org/mailman/listinfo/swift-evolution



More information about the swift-evolution mailing list