142 votes

Différence entre la propriété et sur le terrain en c# 3.0 +

Je me rends compte que cela semble être un double de Ce qui est la différence entre un champ et une propriété en C#? mais ma question a une légère différence (de mon point de vue):

Maintenant qu'en C# 3.0, je peux déclarer une propriété comme ceci:

public string MyString { get; set; }

considérant que le compilateur fait quelque chose comme de la création du domaine privé (autant que je sache) quelle est la différence entre la déclaration ci-dessus et:

public string myString;

?

Edit: j'ai probablement ne pas expliquer ce que je voulais dire très bien.

Une fois que je sais que je ne veux pas utiliser ma classe avec des techniques qui ne fonctionne que sur les propriétés" et je n'ai pas besoin de validation et voulez utilisez les get/set

quelle est la différence (sauf le style/développement futur) -comme un certain type de contrôle dans l'établissement de la propriété ?

165voto

Brian Rasmussen Points 68853

Les champs et les propriétés ont la même apparence, mais ils ne le sont pas. Des propriétés et des méthodes en tant que tel il y a certaines choses qui ne sont pas pris en charge pour les propriétés, et certaines choses qui peuvent se produire avec des propriétés, mais jamais dans le cas de champs.

Voici une liste de différences:

  • Les champs peuvent être utilisées comme entrée d' out/ref arguments. Les propriétés ne peuvent pas.
  • Un champ de toujours donner le même résultat lorsqu'il est appelé plusieurs fois (si nous laissons de problèmes avec plusieurs threads). Une propriété, par exemple de type DateTime.Maintenant n'est pas toujours égale à elle-même.
  • Propriétés peuvent lever des exceptions - les champs ne sera jamais le faire.
  • Les propriétés peuvent avoir des effets secondaires ou de prendre un temps très long à exécuter. Les champs n'ont pas d'effets secondaires et sera toujours aussi vite que possible pour le type donné.
  • Propriétés de support différent de l'accessibilité pour les getters/setters - champs ne sont pas (mais les champs peuvent être apportées readonly)
  • Lors de l'utilisation de la réflexion les propriétés et les champs sont considérés comme différents MemberTypes de sorte qu'ils sont situés différemment (GetFields vs GetProperties par exemple)
  • Le Compilateur JIT peut traiter l'accès à la propriété de façon très différente par rapport à l'accès aux champs. Il peut cependant compiler vers le bas à l'identique du code natif, mais la portée de la différence est là.

119voto

Mark Ingram Points 24995

L'Encapsulation.

Dans le deuxième exemple que vous venez de définir une variable, dans la première, il y a un getter / setter autour de la variable. Donc, si vous décidez que vous voulez valider la variable à une date ultérieure -, il sera beaucoup plus facile.

De Plus, ils présentent de façon différente dans Intellisense :)

Edit: mise à Jour de l'OPs mise à jour de question - si vous souhaitez ignorer les autres suggestions ici, l'autre raison est que c'est tout simplement pas bon OO design. Et si vous n'avez pas une très bonne raison de le faire, toujours choisir une propriété sur une variable publique / champ.

43voto

Dustin Campbell Points 6323

Quelques différences rapides et évidentes

  1. Une propriété peut avoir des mots-clés de l’accesseur.
  2. Une propriété peut être substituée dans les descendants.

14voto

AnthonyWJones Points 122520

La différence fondamentale est qu’un champ est une position en mémoire où sont stockées les données du type spécifié. Une propriété représente une ou deux unités de code qui sont exécutées pour récupérer ou définir une valeur du type spécifié. L’utilisation de ces méthodes d’accesseur est syntaxiquement masquée à l’aide d’un membre qui semble se comporter comme un champ (en ce qu’il peut apparaître de chaque côté d’une opération de cession).

11voto

sysexpand Points 1038

Les accesseurs sont plus que des champs. D'autres l'ont déjà souligné plusieurs différences importantes, et je vais en ajouter un de plus.

Propriétés de prendre part à des classes d'interface. Par exemple:

interface IPerson
{
    string FirstName { get; set; }
    string LastName { get; set; }
}

Cette interface peut être satisfait de plusieurs façons. Par exemple:

class Person: IPerson
{
    private string _name;
    public string FirstName
    {
        get
        {
            return _name ?? string.Empty;
        }
        set
        {
            if (value == null)
                throw new System.ArgumentNullException("value");
            _name = value;
        }
    }
    ...
}

Dans cette implémentation, nous visons à protéger à la fois l' Person de la classe d'entrer dans un état non valide, ainsi qu'à l'appelant d'obtenir nulle de la non attribuées à la propriété.

Mais on pourrait pousser la conception même de plus loin. Par exemple, l'interface peut ne pas traiter avec le setter. Il est tout à fait légitime de dire que les consommateurs de IPerson interface sont uniquement intéressés par l'obtention de la propriété, et non dans l'établissement:

interface IPerson
{
    string FirstName { get; }
    string LastName { get; }
}

Mise en oeuvre préalable de l' Person classe répond à cette interface. Le fait qu'il permet à l'appelant également définir les propriétés de sens du point de vue des consommateurs (qui consomment IPerson). Fonctionnalités supplémentaires de la mise en œuvre concrète n'est prise en considération, par exemple, le constructeur:

class PersonBuilder: IPersonBuilder
{
    IPerson BuildPerson(IContext context)
    {

        Person person = new Person();

        person.FirstName = context.GetFirstName();
        person.LastName = context.GetLastName();

        return person;

    }
}

...

void Consumer(IPersonBuilder builder, IContext context)
{
    IPerson person = builder.BuildPerson(context);
    Console.WriteLine("{0} {1}", person.FirstName, person.LastName);
}

Dans ce code, le consommateur ne connaît pas bien les setters - il n'est pas à lui de les connaître. Consommateur doit simplement les méthodes de lecture, et il obtient des getters de l'interface, c'est à dire le contrat.

Un autre tout à fait valable, la mise en œuvre de l' IPerson serait immuable classe personne et une personne correspondante de l'usine:

class Person: IPerson
{
    public Person(string firstName, string lastName)
    {

        if (string.IsNullOrEmpty(firstName) || string.IsNullOrEmpty(lastName))
            throw new System.ArgumentException();

        this.FirstName = firstName;
        this.LastName = lastName;

    }

    public string FirstName { get; private set; }

    public string LastName { get; private set; }

}

...

class PersonFactory: IPersonFactory
{
    public IPerson CreatePerson(string firstName, string lastName)
    {
        return new Person(firstName, lastName);
    }
}
...
void Consumer(IPersonFactory factory)
{
    IPerson person = factory.CreatePerson("John", "Doe");
    Console.WriteLine("{0} {1}", person.FirstName, person.LastName);
}

Dans cet exemple de code de consommation, une fois encore, n'a pas connaissance de remplir les propriétés. Les consommateurs ne traite qu'avec les getters et la mise en œuvre concrète (et la logique métier derrière elle, comme un test si le nom est vide) est laissé à des classes spécialisées - les constructeurs et les usines. Toutes ces opérations sont tout à fait impossible avec des champs.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X