61 votes

Que font les accolades après la nouvelle instruction C #?

Étant donné le code ci-dessous, quelle est la différence entre la façon dont position0 est initialisé et la façon position1 est initialisé? Sont-ils équivalents? Sinon, quelle est la différence.

 class Program
{
    static void Main(string[] args)
    {
        Position position0 = new Position() { x=3, y=4 };

        Position position1 = new Position();
        position1.x = 3;
        position1.y = 4;
    }
}

struct Position
{
    public int x, y;
}
 

59voto

Jon Skeet Points 692016

Ils ne sont pas tout à fait équivalent - au moins pas dans le cas général. Le code à l'aide d'un initialiseur d'objet est plus proche de ceci:

Position tmp = new Position();
tmp.x = 3;
tmp.y = 4;
Position position1 = tmp;

En d'autres termes, l'affectation à la variable se produit uniquement après les propriétés ont été définies. Maintenant dans le cas où vous êtes de déclarer une nouvelle variable locale, qui n'a pas de réelle importance, et le compilateur peut bien optimiser votre premier formulaire. Mais, logiquement, il n'importe. Considérer:

Position p1 = new Position { x = 10, y = 20 };

p1 = new Position { x = p1.y, y = p1.x };

Si cela n'est que la cession p1 d'abord, vous finirais avec 0 pour les deux p1.x et p1.y. Alors que c'est en fait équivalent à:

Position tmp = new Position();
tmp.x = 10;
tmp.y = 20;
Position p1 = tmp;

tmp = new Position();
tmp.x = p1.y; // 20
tmp.y = p1.x; // 10
p1 = tmp;

EDIT: je viens de réalisé que vous êtes en utilisant une structure plutôt qu'une classe. Que peut faire quelques subtiles différences... mais vous avez presque certainement ne devriez pas être à l'aide d'une mutable struct pour commencer :)

47voto

Joshua Rodgers Points 2932

Initialiseurs d'objets et de collections, utilisés pour initialiser des champs sur un objet.

http://msdn.microsoft.com/en-us/library/bb384062.aspx

Ils produisent une IL presque équivalente. Jon Skeet a la réponse sur ce qui se passe vraiment.

7voto

Marc Gravell Points 482669

C'est un objet initialiser, et permet simplement de vous attribuer des valeurs dans une seule expression. Plus important encore, cela fonctionne aussi à l'intérieur de LINQ un pour les types anonymes (sinon immuable). Il y a aussi une semblable collection initialiser la syntaxe pour addi articles de nouvelles collections.

Notez qu'il y a une subtile problème de synchronisation qui peut être utile; avec initialisers les affectations/ajoute tous se avant de la variable est affectée, ce qui peut aider à arrêter d'autres threads voir incomplète de l'objet. Vous auriez besoin d'une variable supplémentaire pour obtenir le même résultat.

2voto

SLaks Points 391154

Vos deux exemples de code généreront un IL identique. (Au moins dans les versions Release)

1voto

Pieter van Ginkel Points 17057

Ce sont entièrement équivalents. En fait, le compilateur transforme simplement la première version en seconde.

La seule différence entre les deux est qu'avec le premier, vous pouvez faire de belles améliorations, comme passer la version initialisée à une méthode:

 DoSomethingWithPoint(new Position() { x=3, y=4 });
 

C'est beaucoup plus de lignes de code que le deuxième exemple d'initialisation.

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