This proposal is excellent stuff!
If we must have 2 variables to represent 1 value, I'll toss Slice
in as a suffix (instead of Portion
) into the Bikeshedding mix for secondsSlice
& nanosecondsSlice
. Could we not do, a single value so that transitioning to a future Int128
type feels more natural?
public struct Duration: Sendable {
typealias Components = (high: Int64, low: Int64)
public var rawValue: Components { get }
}
However, it feels like this is just emblematic of the larger issue: 128-bit storage. (See Below)
TL;DR - Prototype Tests already have (and have for years had) a DoubleWidth<FixedWidthInteger>
implementation!
@Philippe_Hausler is right, the answer is to expose the storage-- Nothing against quintillionths, but I wouldn't call it attoseconds
I'd jump to RawRepresentable where RawValue == Int128
and expose Duration
storage with rawValue
.
It's exactly the right thing to use here and (so far) Swift has only continued to flirt with Arbitrary-Precision Integers
or even just straight-up Int128
. The Swift repo's Tests have sported both a DoubleWidth<FixedWidthInteger>
(swift/DoubleWidth.swift.gyb at main Ā· apple/swift Ā· GitHub) and a _BigInt
(swift/BigInt.swift at main Ā· apple/swift Ā· GitHub) implementation for years. [NOTE: Result<T>
was in Tests before Swift 2 and only moved to the Standard Library in Swift 5. We should revisit this directory's goodies more often.]
Numerics also has some work on Arbitrary-Precision Integers
(Arbitrary-precision bigints Ā· Issue #5 Ā· apple/swift-numerics Ā· GitHub) .
When it comes to natural Swift-ness, look-and-feel are paramount to usability. This "2 variables == 1 value" paradigm doesn't feel natural in a language where building up value types is such a focus. At least for me, this is what I want out of Duration
:
public struct Duration: Sendable {
public var rawValue: Int128 { get }
}
extension Duration: RawRepresentable { }
I would settle for var rawValue: DoubleWidth<Int64>
. If we need to shim this with a new value type under the covers for a few years, let's do that rather than put some "2 variables == 1 value" stuff in the Standard Library. At least that way we could avoid or at least minimize, some potentially code-breaking update in a future Swift with Int128
or Arbitrary-Precision Integers
.
I can live with 2 properties; but we didn't do this with Concurrency, nor Distributed Actors or all the various SwiftUI-related proposals-- in those cases if something came up, solve the problem or implement a work-around until LLVM could implement a fix (Evolution is still removing work-arounds on Concurrency features and will be until at least Swift 5.6).
2 properties is a work-around, but it just feels like overhead for implementations.
Anyway, great job everyone! I'm very much looking forward to this one! (assuming we encounter no temporal anomalies or time-loops.)