Int to UInt (y viceversa) bit casting en Swift

Estoy buscando una forma directa de convertir los valores de bit de un Int a UInt y viceversa. Por ejemplo (usando los integers de 8 bits para simplificar) quiero lograr lo siguiente:

let unsigned: UInt8 = toUInt8(-1) // unsigned is 255 or 0xff let signed: Int8 = toInt8(0xff) // signed is -1 

Al principio salí con la siguiente solución:

 let unsigned = unsafeBitCast(Int8(-1), UInt8.self) let signed = unsafeBitCast(UInt8(0xff), Int8.self) 

Pero Apple en la documentation "unsafeBitCast ()" indica lo siguiente:

.. Precaución :: Rompe las garantías del sistema de tipo Swift; Usar con extremo cuidado. Casi siempre hay una mejor forma de hacer algo.

¿Alguien tiene el mejor path?

Tu puedes hacer:

 let unsigned = UInt8(bitPattern: Int8(-1)) // -> 255 let signed = Int8(bitPattern: UInt8(0xff)) // -> -1 

Existen muchos inicializadores similares:

 extension Int8 { init(_ v: UInt8) init(_ v: UInt16) init(truncatingBitPattern: UInt16) init(_ v: Int16) init(truncatingBitPattern: Int16) init(_ v: UInt32) init(truncatingBitPattern: UInt32) init(_ v: Int32) init(truncatingBitPattern: Int32) init(_ v: UInt64) init(truncatingBitPattern: UInt64) init(_ v: Int64) init(truncatingBitPattern: Int64) init(_ v: UInt) init(truncatingBitPattern: UInt) init(_ v: Int) init(truncatingBitPattern: Int) init(bitPattern: UInt8) } 

Tomé la ruta de álgebra. Las testings han sido un dolor porque es fácil get un desbordamiento con la tipificación fuerte que rompe la ejecución, PlayGround devolvió un valor negativo de la function toUInt, siguió fallando o dio errores graciosos haciendo un doble casting (abrí un informe de error). De todos modos, esto es lo que terminé con:

 func toUint(signed: Int) -> UInt { let unsigned = signed >= 0 ? UInt(signed) : UInt(signed - Int.min) + UInt(Int.max) + 1 return unsigned } func toInt(unsigned: UInt) -> Int { let signed = (unsigned <= UInt(Int.max)) ? Int(unsigned) : Int(unsigned - UInt(Int.max) - 1) + Int.min return signed } 

Los probé con todos los valores extremos (UInt.min, UInt.max, Int.min, Int.max) y cuando XCode no se vuelve loco parece que funciona, pero parece excesivamente complicado. Lo bastante extraño de la conversión de bits Intuit to Int podría simplemente lograrse con la propiedad hashvalue como en:

 signed = UInt.max.hashValue // signed is -1 

Pero, obviamente, no se garantiza que funcione siempre (debería hacerlo, pero prefiero no correr el riesgo).

Cualquier otra idea será apreciada.

numericCast(...) es lo que estás buscando. Es un set de funciones genéricas que se convierte desde y hacia diferentes types de numbers. Selecciona la implementación correcta en function de los types de su argumento y el tipo de retorno.