2017-03-22 13 views
7

Ten kod działa jest Swift 3:Porównywanie typu literału na szybkim błędzie?

let a = 1 
type(of: a) == Int.self // true 

Jednak zadziwiająco ten kod nie powiedzie:

// error: binary operator '==' cannot be applied to two 'Int.Type' operands 
type(of: 1) == Int.self 

Jaka jest składnia aby drugą pracę porównania, jeśli w ogóle?

Wielkie dzięki.

+0

Co ciekawe, 'niech type1 = typ (z: 1); type1 == Int.self' działa – Sweeper

+0

Jednym z rozwiązań może być zainicjowanie liczby całkowitej takiej jak ta 'type (of: Int (1)) == Int.self // zwraca true' Nie wiem, dlaczego to jest konieczne, chociaż – Frederik

+0

Weirdly, drukowanie 'b' w' let b = type (of: 1) 'drukuje Int. – paper1111

Odpowiedz

4

Myślę, że komunikat o błędzie był mylący. Prawdziwym problemem było to, jak interpretować literalne 1 w drugim wywołaniu. Swift domyślnie do Int podczas definiowania zmiennej:

let a = 1 // a is an Int 

Ale kompilator może go odczytać jako Double, UInt32, CChar itp zależności od kontekstu:

func takeADouble(value: Double) { ... } 
func takeAUInt(value: UInt) { ... } 

takeADouble(value: 1) // now it's a Double 
takeAUInt(value: 1) // now it's a UInt 

type(of:) jest defined jako funkcja ogólna:

func type<Type, Metatype>(of: Type) -> Metatype 

Kompilator nie ma pojęcia w jaki sposób interpretować parametr ogólny Type: czy powinien to być kod Int, UInt, , UInt16 itd.? Tutaj jest błąd dostałem od IBM Swift Sandbox:

Overloads for '==' exist with these partially matching parameter lists 
(Any.Type?, Any.Type?), (UInt8, UInt8), (Int8, Int8), 
(UInt16, UInt16), (Int16, Int16), (UInt32, UInt32), ... 

Można dać coompiler trochę pomóc, powiedzieć to, jakiego rodzaju jest to:

type(of: 1 as Int) == Int.self 
+0

' type (of:) 'jest zdefiniowane jako funkcja ogólna, ale tak naprawdę nie jest wywoływane bezpośrednio - jest traktowane jako specjalny przypadek przez sprawdzanie typu ([zgodnie z komentarzem w implementacji] (https://github.com/apple/swift/blob/master/stdlib/public/core/Builtin.swift#L738)). Dlatego jest to prawdopodobnie tylko błąd sprawdzania typu. Nie powinno być żadnych niejednoznaczności z literałem, ponieważ, jak mówisz, domyślnie będzie to "Int", gdy nie będzie żadnych innych informacji o typie, co oczywiście ma tutaj miejsce. – Hamish

+0

wiele dobrych informacji tutaj. dzięki! – agro1986