Can anyone tell me what is T.Type
when I use JSONDecoder().decode()
?
I think it is type to decode data what I encoded.
So many example use above method like this:
JSONEncoder().decode([People].self, from: data)
If I check that method's definition I can see T.Type
.
I know the generics but what is T.Type
?
What's the difference between just T
and T.Type
?
when we declare some variables, we allocated their types like this
var someValue: Int
, not var someValue: Int.self
What is the T.Type
exactly and Type.self
?
Swift Generics allows us to create a single function and class (or any other types) that can be used with different data types. This helps us to reuse our code.
What is an associated type? An associated type can be seen as a replacement of a specific type within a protocol definition. In other words: it's a placeholder name of a type to use until the protocol is adopted and the exact type is specified.
Solution. A generic function that you might need to use explicit specialization is the one that infer its type from return type—the workaround for this by adding a parameter of type T as a way to inject type explicitly. In other words, we make it infer from method's parameters instead.
Generic Methods A type parameter, also known as a type variable, is an identifier that specifies a generic type name. The type parameters can be used to declare the return type and act as placeholders for the types of the arguments passed to the generic method, which are known as actual type arguments.
T.Type
is used in parameters and constraints to mean "the type of the thing itself, not an instance of the thing".
For example:
class Example {
static var staticVar: String { return "Foo" }
var instanceVar: String { return "Bar" }
}
func printVar(from example: Example) {
print(example.instanceVar) // "Bar"
print(example.staticVar) // Doesn't compile, _Instances_ of Example don't have the property "staticVar"
}
func printVar(from example: Example.Type) {
print(example.instanceVar) // Doesn't compile, the _Type_ Example doesn't have the property "instanceVar"
print(example.staticVar) // prints "Foo"
}
You get a reference to a Type's .Type
(the Type object itself) at runtime by calling TheType.self
. The syntax TheType.Type
is used in type declarations and type signatures only to indicate to the compiler the instance vs. type distinction. You can't actually get a reference to, for example, Int
's type at runtime or in your function implementations by calling Int.Type
. You would call Int.self
In the example code var someValue: Int
, the specific notation identifier: Type
(in this case, someValue: Int
) means that someValue will be an instance of Int. If you wanted someValue to be a reference to the actual type Int, you would write var someValue: Int.Type = Int.self
Remember that the .Type
notation is only used when declaring types and type signatures to the compiler, and the .self
property is used in actual code to retrieve a reference to the type object itself at execution time.
The reason why JSONDecoder().decode
requires a parameter of T.Type
(where T
conforms to Decodable
) is because any type conforming to Decodable
has an initializer init(from decoder: Decoder)
. The decode
method will need to call this init method on a type that conforms to Decodable
, not on an instance of a type that conforms to Decodable
. For example:
var someString: String = ""
someString.init(describing: 5) // Not possible, doesn't compile. Can't call an initializer on an _instance_ of String
var someStringType: String.Type = String.self
someStringType.init(describing: 5) // Iniitializes a String instance "5"
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With