Any y AnyObject en Swift. ¿Cuál es su diferencia?

Mucho tiempo en mis proyectos cuando escribía cuando usaba Any type, por ejemplo, cuando procesaba datos JSON. Pero también sabía que hay un segundo tipo: AnyObject . Y recientemente, he estado pensando en la diferencia entre estos dos tipos.

De acuerdo con la documentación de Apple:

  • Cualquiera : puede representar una instancia de cualquier tipo
  • AnyObject : puede representar una instancia de cualquier clase

Para decirlo un poco más fácil, entonces:

  • Cualquiera se usa para todos los tipos.
  • AnyObject : se usa para los tipos de clase

Verifiquemos en la práctica estos dos tipos. Comencemos con el tipo Any .

Para hacer esto, cree una matriz de tipo Any e imprímala.

let anyArray: [Any] = ["Macbook", 1, 2] print(anyArray) Console: ["Macbook", 1, 2] 

Como podemos ver, Any le permite trabajar con diferentes tipos de datos al mismo tiempo (String, Int).
De acuerdo con la documentación, los elementos ( String e Int ) en esta matriz son estructuras que son tipos de valores, por lo tanto, en teoría, AnyObject no debería funcionar.

Para verificar esto, cree una matriz idéntica de tipo AnyObject .

 let anyObjectArray: [AnyObject] = ["Macbook", 1, 2] 

Como se esperaba, el compilador nos da un error sobre la imposibilidad de convertir el tipo "String / Int" al tipo AnyObject

Error del compilador
No se puede convertir el valor del tipo "Int" al tipo de elemento esperado "AnyObject"
No se puede convertir el valor del tipo "Int" al tipo de elemento esperado "AnyObject"
No se puede convertir el valor del tipo "Cadena" al tipo de elemento esperado "AnyObject"

Pero intentemos llevar nuestros tres tipos a AnyObject e imprimir el resultado.

 let anyObjectArray: [AnyObject] = ["Macbook" as AnyObject, 1 as AnyObject, 2 as AnyObject] print(anyObjectArray) Console: [Macbook, 1, 2] 

El error del compilador ha desaparecido. Como podemos ver, una cadena de Macbook se ve claramente como una cadena, pero no tiene las comillas habituales como el tipo de cadena en Swift.

Intentemos imprimir la matriz usando un bucle para verificar su tipo real.

 for item in anyObjectArray { if item is String { print("\(item)   String") } else if item is Int { print("\(item)   Int") } } Console: Macbook   String 1   Int 2   Int 

Una cadena es de tipo cadena. Como se dijo antes, las cadenas en Swift son estructuras, no tipos de clases. Por lo tanto, no deberíamos poder usarlos como AnyObject.

Realicemos un par de experimentos más con nuestra matriz. Intentemos verificar si hay tipos de Objective - C: NSString y NSNumber .

 for item in anyObjectArray { if item is NSString { print("\(item)   NSString") } else if item is NSNumber { print("\(item)   NSNumber") } } Console: Macbook   NSString 1   NSNumber 2   NSNumber 

Entonces, ¿por qué está pasando esto?


Como parte de su compatibilidad con Objective - C, Swift ofrece formas convenientes y eficientes de trabajar con las plataformas Cocoa.

Swift convertirá automáticamente algunos tipos de Objective - C a tipos de Swift, y algunos tipos de Swift a tipos de Objective - C. Los tipos que se pueden convertir entre Objetivo - C y Swift se denominan concatenados .

En otras palabras, el compilador hace todo lo posible para ser flexible en el manejo de estos tipos al convertir y crear automáticamente "puentes", al mismo tiempo que evita los bloqueos de la aplicación.

¿Cuándo usar AnyObject?


Como se indica en la documentación de Apple, AnyObject se puede utilizar para trabajar con objetos derivados de Class pero que no tienen una clase raíz común.

En Swift 3, el tipo de identificación en Objetivo - C ahora se asigna a Cualquier tipo en Swift, que describe el valor de cualquier tipo, ya sea una clase, enumeración, estructura o cualquier otro tipo de Swift. Este cambio hace que las API de Objective - C sean más flexibles en Swift, porque los tipos de valor definidos por Swift pueden pasarse a las API de Objective - C y recuperarse como tipos de Swift, eliminando la necesidad de tipos de "bloques" manuales.

Por lo tanto, es aconsejable usar AnyObject cuando desee restringir el protocolo para que pueda usarse solo con clases y Any en otros casos .

Apple agrega :
Use Any y AnyObject solo cuando necesite explícitamente el comportamiento y las capacidades que proporcionan. Siempre es mejor ser preciso sobre los tipos que espera usar en su código.

Source: https://habr.com/ru/post/483494/


All Articles