40 votes

Pourquoi un arbre d'expression ne peut-il pas contenir une spécification d'argument nommé ?

En utilisant AutoMapper, j'ai trouvé un endroit où un argument nommé aurait été très bien adapté :

.ForMember(s => s.MyProperty, opt => opt.MapFrom(s => BuildMyProperty(s, isAdvanced: false)))

Mais le compilateur m'a crié dessus :

Un arbre d'expression ne peut pas contenir de spécification d'un argument nommé.

J'ai donc dû revenir à :

.ForMember(s => s.MyProperty, opt => opt.MapFrom(s => BuildMyProperty(s, false)))

Quelqu'un sait-il pourquoi le compilateur rejette les arguments nommés dans cette situation ?

31voto

Eric Lippert Points 300275

Considérez ce qui suit :

static int M() { Console.Write("M"); return 1; }
static int N() { Console.Write("N"); return 2; }
static int Q(int m, int n) { return m + n; }
...
Func<int> f = ()=>Q(n : N(), m: M());
Expression<Func<int>> x = ()=>Q(n : N(), m: M());
Func<int> fx = x.Compile();
Console.WriteLine(f());
Console.WriteLine(fx());

Vous êtes d'accord j'espère que les deux dernières lignes doivent faire exactement la même chose, n'est-ce pas ? Qui est d'imprimer NM3 .

Maintenant, quels appels de la bibliothèque de l'arbre d'expression voudriez-vous que la conversion de l'arbre d'expression génère pour garantir cela ? Il n'y en a pas ! Nous sommes donc confrontés aux choix suivants :

  1. Implémentez la fonctionnalité dans la bibliothèque d'arbres d'expression. Ajouter une transformation dans le moteur d'abaissement de l'arbre d'expression qui préserve l'ordre d'exécution des arguments nommés. Implémenter le code dans la bibliothèque Compile qui prend en compte l'ordre d'exécution.
  2. Faire x = ()=>Q(n : N(), m: M()); peut en fait être mis en œuvre comme x = ()=>Q(M(), N()); et être incompatible avec la version sans arbre d'expression.
  3. Interdire les arguments nommés dans les arbres d'expression. Implémentez un message d'erreur à cet effet.

(1) est agréable, mais coûteux. (2) est un échec ; nous ne pouvons pas en bonne conscience introduire ce genre de "gotcha". (3) est bon marché mais irritant.

Nous avons choisi (3).

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