Introducción: ¿por qué la pregunta sobre auto-propiedades reunió miles de visitas?
\n\nSi alguna vez ha programado en C#, seguramente se ha encontrado con una pregunta simple pero importante: "¿Cómo asignar correctamente un valor inicial a una auto-propiedad?". Esta pregunta en Stack Overflow ha reunido decenas de miles de visitas, y no es para menos. La aparente simplicidad oculta muchas trampas.
\n\nImagine: crea una clase User, y desea que la propiedad Name no sea null por defecto, sino una cadena vacía. Parece sencillo, ¿qué podría salir mal? Pero en la práctica, los desarrolladores cometen errores típicos de inicialización de propiedades en C# que provocan NullReferenceException o comportamientos inesperados.
En este artículo analizaremos el TOP-5 de errores y mostraremos cómo evitarlos. Conocerá enfoques modernos, desde C# 6 hasta C# 12, y entenderá qué método elegir para su proyecto.
\n\n\n\n
Error n.º 1: Ignorar la inicialización de auto-propiedades
\n\nEl error más común es no asignar un valor inicial para tipos de referencia. Muchos principiantes escriben:
\n\npublic class User\n{\n public string Name { get; set; } // null por defecto\n public List<string> Roles { get; set; } // null\n}\n\nEn C#, las auto-propiedades para tipos de referencia son null por defecto. Esto provoca problemas con NullReferenceException cuando olvida asignar un valor antes de usarlas.
¿Cómo solucionarlo?
\nSiempre asigne explícitamente un inicializador de auto-propiedad en C#. La forma más sencilla es usar la sintaxis de C# 6:
\n\npublic class User\n{\n public string Name { get; set; } = string.Empty;\n public List<string> Roles { get; set; } = new List<string>();\n}\n\n\n\n\nConsejo: Use
\nstring.Emptyen lugar de comillas vacías: mejora la legibilidad y sigue las mejores prácticas de C#.
\n\n
Error n.º 2: Inicialización en el constructor sin considerar la cadena de llamadas
\n\nOtro error frecuente es establecer el valor por defecto en C# solo en el constructor, ignorando los inicializadores de propiedades. Esto puede causar confusión, especialmente con herencia.
\n\npublic class BaseClass\n{\n public int Value { get; set; }\n\n public BaseClass()\n {\n Value = 10;\n }\n}\n\npublic class DerivedClass : BaseClass\n{\n public DerivedClass()\n {\n // Value ya = 10, pero podemos sobrescribirlo\n }\n}\n\nProblema: si agrega un inicializador a la propiedad Value y mantiene la asignación en el constructor, el orden de ejecución puede sorprenderle. Los inicializadores se ejecutan antes del cuerpo del constructor de la clase base, pero después de la llamada al constructor de la clase derivada.
¿Cómo evitarlo?
\nElija un solo método: o inicializador o constructor. Es mejor optar por los inicializadores de auto-propiedades en C#, ya que son más predecibles y concisos.
\n\npublic class BaseClass\n{\n public int Value { get; set; } = 10; // Única fuente de verdad\n}\n\n\n\n
Error n.º 3: Usar campos readonly en lugar de auto-propiedades
\n\nAlgunos desarrolladores, al intentar asignar un valor inicial, abandonan las auto-propiedades y usan campos públicos:
\n\npublic class Config\n{\n public readonly int MaxRetries = 3; // Error: violación de encapsulación\n}\n\nEsta es una mala práctica. Los campos violan la encapsulación: no podrá agregar lógica en el getter/setter sin cambiar la API. Además, al serializar o usar en WPF/Blazor, esto generará problemas.
\n\nEnfoque correcto
\nUse auto-propiedades con inicialización o propiedades init-only de C# 9:<