Estoy creando un cliente Reddit con fines de aprendizaje. Necesito tener un archivo con constantes. Estaba pensando en importar el archivo en el Reddit-Prefix.pcharchivo para que las constantes estén disponibles para todos los archivos. ¿Es una buena forma de hacer las cosas? Además, hice mi investigación y encontré varios métodos para crear constantes, pero no sé cuál usar:
#definemacroconststatic constextern constenum
Entonces, ¿cuál es la forma preferida? ¿Qué es la convención? Sé que "depende", pero mi pregunta más específica es: ¿Cuáles son los casos de uso para cada una de esas soluciones?
Además, si lo uso extern const, ¿necesito importar el archivo, o las constantes estarán disponibles globalmente sin importar el archivo?
Una cosa que podría concluir lógicamente es que enumes la mejor opción al definir algo como dominios de error personalizados (¿estoy realmente en lo cierto?). ¿Pero qué hay de los demás?
fuente

enumsolo es útil para valores integrales.#definey las constantes pueden ser de cualquier tipo de datos.const,static constyextern constson todos iguales excepto por el alcance. Entonces, en realidad solo hay tres opciones.Respuestas:
La primera pregunta es qué alcance desea que tengan sus constantes, que en realidad son dos preguntas:
Si son específicos e internos de una sola clase, declare como
static consten la parte superior del archivo .m, así:Si pertenecen a una sola clase pero deben ser públicas / utilizadas por otras clases, declare como
externen el encabezado y defínalos en el .m:Si deben ser globales, declararlos en un encabezado y definirlos en un módulo correspondiente, específicamente para esas constantes.
Puede mezclarlos y combinarlos para diferentes constantes con diferentes niveles de cuán global desea que sean, y para diferentes constantes globales que simplemente no pertenecen juntas; puede colocarlas en módulos separados, cada uno con su propio encabezado, si querer.
¿Por qué no
#define?La vieja respuesta es "las macros no tienen información de tipo", pero los compiladores de hoy en día son bastante inteligentes al hacer toda la verificación de tipo para los literales (a qué se expanden las macros) y las variables.
La respuesta moderna es porque el depurador no sabrá sobre sus macros. No se puede decir
[myThing addObserver:self forKey:MyThingNotificationKey]en un comando de depurador siMyThingNotificationKeyes una macro; el depurador solo puede saberlo si es una variable.¿Por qué no
enum?Bueno, rmaddy me ganó en los comentarios:
enumsolo puede definir constantes enteras. Cosas como números de identificación de serie, máscaras de bits, códigos de cuatro bytes, etc.Para esos fines,
enumes genial y absolutamente deberías usarlo. (Aún mejor, use las macrosNS_ENUMyNS_OPTIONS.) Para otras cosas, debe usar otra cosa;enumno hace nada más que enteros.Y otras preguntas
Probablemente inofensivo, pero probablemente excesivo. Importe sus encabezados constantes donde los necesite.
#define: Bastante limitado. Honestamente, no estoy seguro de que haya una buena razón para usar esto para las constantes.const: Lo mejor para las constantes locales. Además, debe usar esto para uno que declaró en un encabezado y que ahora está definiendo.static const: Mejor para constantes específicas de archivo (o específicas de clase).extern const: Debe usar esto al exportar una constante en un encabezado.Debe importar el archivo, ya sea en cada archivo donde lo usa o en el encabezado del prefijo.
fuente
static NSString *consten el.harchivo por completo?static NSString *const foo = @"foo";, su encabezado determina cuál es la cadena, y debe ser la misma en todas partes: si alguna vez cambia la cadena y las diferentes partes usan diferentes versiones del encabezado con una cadena diferente, las cadenas no coincidirán en la ejecución hora. En un marco, desea proporcionar acceso solo al símbolo y dejar que el marco sea la única fuente del verdadero valor de ese símbolo, para que todos obtengan la misma cadena desde un solo lugar. Eso es lo queexternte atrapa.#defines: no se garantiza que tengan la misma dirección en la memoria (dependiendo de cómo se declaren, pueden asignar una nueva instancia cada vez que se usan), por lo que el usomyObject == MyDefineno siempre funcionará como se esperaba, pero lomyObject == MyStaticConstharé.static NSString *constlugar destatic NSString const*?? ¿Alguna diferencia?static NSString const *es lo mismostatic const NSString *y significa "un puntero (variable) a una NSString constante", lo cual es un poco inútil aquí ya que NSString ya es inmutable. Lo que solo quieresstatic NSString * const, que es un "puntero constante a un NSString"FOUNDATION_EXPORT
Considere usar
FOUNDATION_EXPORTun poco más de compatibilidad queexternya que está definido en la base y compila a formatos compatibles para C, C ++ y Win32.Como se define en NSObjCRuntime.h
fuente