Hi,
I am designing a new deserialization API. Looking for advice on return type overloading vs. specifying the decode-as type in a method argument.
Looking at the Decodable APIs in Foundation the decode methods, such as in SingleValueDecodingContainer, has the type as an explicit argument, for example:
func decode(_ type: String.Type) throws -> String
func decode(_ type: Int.Type) throws -> Int
func decode<T>(_ type: T.Type) throws -> T where T : Decodable
Rather than overloading only on the return type:
func decode() throws -> String
func decode() throws -> Int
func decode<T>() throws -> T where T : Decodable
Considering that one common use case is decoding to properties in an init method, the former Foundation Decodable-like design requires repeating the property type in each decode call as follows:
struct SomeFoo {
let a: Int // Int
let b: String
init(_ decoder: Decoder) throw {
a = try decoder.decode(Int.self) // Yes, again, it's an Int
b = try decoder.decode(String.self)
}
}
While the argument-less version would simply be:
struct SomeFoo {
let a: Int
let b: String
init(_ decoder: Decoder) {
a = try decoder.decode()
b = try decoder.decode()
}
}
Apart from type-checker performance (I remember this being a concern earlier in Swift's history, is it still relevant in this scenario?), are there any good reasons to have the type as an explicit argument?