Campos públicos versus propiedades automáticas

A menudo nos dicen que debemos proteger la encapsulación haciendo métodos getter y setter (propiedades en C #) para los campos de clase, en lugar de exponer los campos al mundo exterior.

Pero hay muchas veces en que un campo está ahí para contener un valor y no requiere ningún cálculo para obtener o establecer. Para estos, todos haríamos este número:

public class Book { private string _title; public string Title { get{ return _title; } set{ _title = value; } } } 

Bueno, tengo una confesión, no podría soportar escribir todo eso (realmente, no era tener que escribirlo, sino tener que verlo), así que fui deshonesto y usé los campos públicos.

Luego viene C # 3.0 y veo que agregaron propiedades automáticas:

 public class Book { public string Title {get; set;} } 

que es más ordenado, y estoy agradecido por ello, pero en realidad, ¿qué es tan diferente que simplemente hacer un campo público?

 public class Book { public string Title; } 

En una pregunta relacionada que tuve hace algún tiempo, había un enlace a una publicación en el blog de Jeff, que explicaba algunas diferencias.

Propiedades vs. Variables Públicas

  • La reflexión funciona de manera diferente en variables y propiedades, por lo que si confías en la reflexión, es más fácil usar todas las propiedades.
  • No puedes enlazar datos con una variable.
  • Cambiar una variable a una propiedad es un cambio radical. Por ejemplo:

     TryGetTitle(out book.Title); // requires a variable 

Ignorando los problemas de API, lo que más valoro sobre el uso de una propiedad es la depuración.

El depurador CLR no admite puntos de interrupción de datos (la mayoría de los depuradores nativos lo hacen). Por lo tanto, no es posible establecer un punto de corte en la lectura o escritura de un campo en particular en una clase. Esto es muy limitante en ciertos escenarios de depuración.

Debido a que las propiedades se implementan como métodos muy delgados, es posible establecer puntos de interrupción en la lectura y escritura de sus valores. Esto les da una gran ventaja sobre los campos.

El cambio de un campo a una propiedad rompe el contrato (por ejemplo, requiere la recomstackción de todos los códigos de referencia). Entonces, cuando tiene un punto de interacción con otras clases, cualquier miembro público (y generalmente protegido), desea planificar el crecimiento futuro. Hazlo usando siempre propiedades.

No es nada para convertirlo en una propiedad de auto hoy, y 3 meses después se dará cuenta de que quiere que sea de carga lenta, y ponga un cheque nulo en el captador. Si utilizó un campo, este es un cambio de recomstackción en el mejor de los casos, e imposible en el peor, según quién y qué más dependa de sus ensamblajes.

Solo porque nadie lo mencionó: No puede definir campos en Interfaces. Entonces, si tiene que implementar una interfaz específica que define propiedades, las propiedades automáticas a veces son una característica realmente agradable.

Una gran diferencia que a menudo se pasa por alto y no se menciona en ninguna otra respuesta: anulación . Puede declarar propiedades virtuales y anularlas, mientras que no puede hacer lo mismo para los campos de miembros públicos.

Otra ventaja de las propiedades implementadas automáticamente sobre los campos públicos es que puede hacer que los accesos de conjunto sean privados o protegidos, proporcionando la clase de objetos donde se definió un mejor control que el de los campos públicos.

Se trata de versiones y estabilidad de API. No hay diferencia, en la versión 1, pero más adelante, si decide que necesita hacer de esto una propiedad con algún tipo de error al verificar en la versión 2, no tiene que cambiar su API, no hay cambios de código, en ningún otro lugar, excepto la definición de la propiedad.

No hay nada de malo en hacer un campo public . Pero recuerde que la creación de getter/setter con campos private no tiene encapsulamiento. OMI, si no le importan otras características de una Property , también podría hacerlo public .

Si luego decide comprobar que el título es único, al compararlo con una colección o una base de datos, puede hacerlo en la propiedad sin cambiar ningún código que dependa de ella.

Si elige solo un atributo público, tendrá menos flexibilidad.

La flexibilidad adicional sin romper el contrato es lo más importante para mí sobre el uso de propiedades y, hasta que realmente necesite la flexibilidad, la autogeneración tiene más sentido.

Una cosa que encuentro muy útil, así como todas las razones de código y prueba, es que si se trata de una propiedad frente a un campo es que el IDE de Visual Studio muestra las referencias de una propiedad pero no de un campo.

    Intereting Posts