D'autres l'ont déjà souligné qu'il existe une infinité de possibles délégué des types que vous pourriez dire; ce qui est si spécial à propos de Func
qu'il mérite d'être la valeur par défaut à la place de Predicate
ou Action
ou toute autre possibilité? Et, pour les lambdas, pourquoi est-il évident que l'intention est de choisir le délégué forme, plutôt que l'expression de la forme de l'arbre?
Mais on pourrait dire qu' Func
est spécial, et que le type inféré d'un lambda, d'anonymes ou de la méthode est la touche Func de quelque chose. Nous serions tout de même avoir toutes sortes de problèmes. Quels types aimeriez-vous être déduit pour les cas suivants?
var x1 = (ref int y)=>123;
Il n'y a pas d' Func<T>
type qui prend un ref quoi que ce soit.
var x2 = y=>123;
Nous ne connaissons pas le type du paramètre formel, même si nous savons que le retour. (Ou est-ce nous? C'est le retour de type int? longue? court? octet?)
var x3 = (int y)=>null;
Nous ne connaissons pas le type de retour, mais il ne peut pas être nulle. Le type de retour peut être n'importe quel type de référence ou de tout nullable type de valeur.
var x4 = (int y)=>{ throw new Exception(); }
Encore une fois, nous ne connaissons pas le type de retour, et cette fois, il peut être vide.
var x5 = (int y)=> q += y;
Est celui destiné à être un vide-retour de la déclaration lambda ou quelque chose qui renvoie la valeur qui a été affecté à q? Les deux sont légales; qui devrions-nous choisir?
Maintenant, vous pourriez dire, eh bien, il suffit de ne pas l'appui de ces fonctionnalités. En plus de soutenir "normal" cas où les types peuvent être réglés. Cela n'aide pas. Comment est-ce que faire de ma vie plus facile? Si la fonctionnalité fonctionne parfois et échoue parfois je dois encore écrire le code pour détecter toutes ces situations de défaillance et de donner un message d'erreur significatif pour chacun d'eux. Nous avons encore à spécifier toutes qu'un comportement, d'un document, d'écrire des tests pour elle, et ainsi de suite. C'est un très coûteux fonctionnalité qui permet d'économiser l'utilisateur peut-être une demi-douzaine de frappes. Nous avons de meilleures façons d'ajouter de la valeur à la langue que de passer beaucoup de temps à écrire des cas de test pour une fonctionnalité qui ne fonctionne pas la moitié du temps et ne fournit pas loin de bénéficier dans les cas où il ne fonctionne pas.
La situation où il est réellement utile:
var xAnon = (int y)=>new { Y = y };
parce qu'il n'y a pas de "speakable" type pour cette chose. Mais nous avons ce problème tout le temps, et il nous suffit d'utiliser la méthode d'inférence de types de déduire le type:
Func<A, R> WorkItOut<A, R>(Func<A, R> f) { return f; }
...
var xAnon = WorkItOut((int y)=>new { Y = y });
et maintenant, la méthode d'inférence de type œuvres ce que la touche func type est.