¿Debo usar propiedades públicas y campos privados o campos públicos para datos?

En gran parte del código que he visto (en SO, thecodeproject.com y tiendo a hacer esto en mi propio código), he visto propiedades públicas que se crean para cada campo privado que una clase contiene, incluso si son las más tipo básico de get; set; get; set; me gusta:

 private int myInt; public int MyInt { get { return myInt; } set { myInt = value } } 

Mi pregunta es: ¿cómo difiere esto de:

 public int MyInt; 

y si deberíamos usar propiedades en lugar de campos públicos, ¿por qué deberíamos usarlos en este caso específico? (No estoy hablando de ejemplos más complejos en los que los getters y los setters realmente hacen algo especial o solo hay un get o set (solo lectura / escritura) en lugar de solo devolver / establecer un valor de un campo privado). ¡No parece agregar ninguna encapsulación adicional, solo da un bonito icono en IntelliSense y se coloca en una sección especial en los diagtwigs de clase!

Ver este artículo http://blog.codinghorror.com/properties-vs-public-variables/

Específicamente

  • 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.

Tres razones:

  1. No puede anular los campos en subclases como las propiedades de usted.
  2. Eventualmente puede necesitar un getter o setter más complejo, pero si se trata de un campo, cambiarlo rompería la API.
  3. Convención. Así es como está hecho.

Estoy seguro de que hay más razones por las que no estoy pensando.

En .Net 3.x puede usar propiedades automáticas como esta:

 public int Age { get; set; } 

en lugar de la forma de la vieja escuela de declarar tus campos privados tú mismo de esta manera:

 private int age; public int Age { get { return age; } set { age = value; } } 

Esto lo hace tan simple como crear un campo, pero sin el problema del cambio de ruptura (entre otras cosas).

Cuando crea un nombre de campo privado y una propiedad pública simple Nombre que realmente obtiene y establece el valor del campo de nombre

 public string Name { get { return name; } } 

y usas esta propiedad en todas partes fuera de tu clase y algún día decidirás que la propiedad Name de esta clase se referirá realmente al campo lastName (o que quieres devolver una cadena “My name:” + name), simplemente cambias el código dentro de la propiedad:

 public string Name { get { return lastName; //return "My name: "+name; } } 

Si estuvieras usando el nombre del campo público en todas partes en el código externo, entonces tendrías que cambiar el nombre a lastName donde sea que lo hayas usado.

Bueno, eso hace la diferencia. Los datos públicos se pueden cambiar sin que la instancia del objeto lo sepa. Usando getters y setters el objeto siempre sabe que se ha realizado un cambio.

Recuerde que encapsular los datos es solo el primer paso hacia un diseño mejor estructurado, no es un objective final en sí mismo.

Debe usar propiedades en los siguientes casos:

  1. Cuando necesita serializar datos en la propiedad a algún formato.
  2. Cuando necesita anular propiedades en clase derivada.
  3. Cuando implemente los métodos get y set con cierta lógica. Por ejemplo, cuando implementa un patrón de Singleton.
  4. Cuando deriva de la interfaz, donde se declaró la propiedad.
  5. Cuando tiene problemas específicos relacionados con Reflection.

¿Depende?

Siempre uso getters & setters, ya que crearon este atajo:

public int Foo {get; conjunto; }

En tiempo de comstackción, está traducido. Ahora no puedes hacerte elegante con eso, pero está ahí, y si necesitas ser elegante, solo lo deletreas más tarde.

Sin importar lo público, lo privado, lo protegido … todo depende de quién quiera que sea capaz de modificar los datos. Usamos mucho la herencia y este es un método muy común para nosotros, por lo que solo los niños pueden editar ciertas propiedades.

 protected _foo; public Foo { get { return _foo; } } //lack of set intentional. 

Hay muchas razones por qué.

Principalmente:

  • Puede hacer otras funciones cuando la variable está configurada
  • Puede evitar la configuración y proporcionar solo obtener
  • Algunas ‘cosas’ solo funcionan en propiedades (DataBinding, por ejemplo)
  • Puede ocultar la implementación de la propiedad [quizás sea una variable ViewState, en ASP.NET).

El punto es: ¿qué sucede si más adelante desea asegurarse de que cada vez que se hace referencia a myInt ocurra algo especial (se escriba un archivo de registro, se cambie a 42, etc.)? No puedes hacer eso sin getters y setters. A veces es conveniente progtwigr para lo que pueda necesitar, no lo que necesita en este momento.

En realidad, si está usando Silverlight, se dará cuenta de que los campos no se pueden establecer como recursos estáticos y, por lo tanto, tendrá que usar una propiedad (incluso para acceder a un const ).

Me di cuenta de que cuando intenté federar los nombres de región, los utilizo en la Guía compuesta (PRISM).

Sin embargo, eso solo es una limitación del lenguaje y, aparte de static campos static / const , siempre uso propiedades.

La idea es que no se debe cambiar accidental o involuntariamente el valor de un campo privado de clase fuera. Cuando utilizas get y set, eso significa que estás cambiando el campo privado de la clase intencionalmente y con conocimiento.

Establecer un valor en un campo privado solo cambia ese campo, pero al crearlos en propiedad puede manejar otros argumentos, por ejemplo, puede llamar a un método después de establecer un valor

 cadena privada _email;
 cadena pública Correo electrónico
 {
     obtener
     {
         devuelve this._email;
     }
     conjunto
     {
         this._email = valor;
         ReplaceList ();  // **
     }
 }




En palabras más simples, la respuesta a su pregunta es los modificadores de acceso, es decir, públicos y privados.

Si utiliza:

 public int myInt; public int MyInt { get { return myInt; } set { myInt = value } } 

entonces, tanto la propiedad MyInt como la variable myInt están disponibles en el proyecto que se modificará. Significa que si su clase supone que A se hereda por clase suponga B, entonces myInt y MyInt ambos están disponibles para modificación y no se puede aplicar ninguna verificación. Supongamos que quiere que myInt value se pueda establecer en la clase deriva si pasa alguna condición particular.

Esto solo se puede lograr haciendo que el campo privado y la propiedad sean públicos. De modo que solo la propiedad está disponible y las condiciones se pueden establecer en función de eso.

No puedo creer que con 11 respuestas, nadie haya dicho esto:

No todos los campos privados deben exponerse como propiedades públicas. Sin duda, debe utilizar propiedades para todo lo que no sea privado, pero debe mantener la privacidad de la mayor parte de su clase.