5

Consider the code below. For the reasons I'd like to figure out C# compiler unable to infer that function Map returns type A w/o explicit type specification when lambda expression is used.

Any reasons or references to documentation for such case that explain the behavior?

class Program
{
    public class A
    {
    }

    public static A Map(dynamic x)
    {
        return new A();
    }

    static void Main(string[] args)
    {
        IEnumerable<dynamic> d = new dynamic[] { };

        // OK
        IEnumerable<A> a1 = d.Select(Map);

        // OK
        IEnumerable<A> a2 = d.Select(x => (A)Map(x));

        // NOT OK
        // Cannot implicitly convert type 'IEnumerable<dynamic>' to 'IEnumerable<A>'
        IEnumerable<A> a3 = d.Select(x => Map(x));
    }
}
Cœur
  • 37,241
  • 25
  • 195
  • 267
Eugene D. Gubenkov
  • 5,127
  • 6
  • 39
  • 71
  • @IanMercer - how does that differ from `a1`? – Damien_The_Unbeliever Mar 31 '17 at 06:51
  • 2
    `dynamic` implies late-binding, so that `Map` call is resolved at run-time, depending on the actual type of `x` at that moment. I think that's why the compiler won't infer the type of `a3`: it cannot (or will not try to) guarantee that `A Map(dynamic x)` will be used. – Pieter Witvoet Mar 31 '17 at 06:56
  • 2
    If you intended it to be a statically-resolved call then **why did you make it dynamic**? – Eric Lippert Mar 31 '17 at 07:45
  • @EricLippert, I'm just using Dapper (micro-ORM) that has handy API to parse result sets via `IEnumerable`. (that moment when Eric Lippert comments your question -- unbelievable :)) – Eugene D. Gubenkov Mar 31 '17 at 08:02
  • @EugeneD.Gubenkov That doesn't change the question. You still went out of your way to actively shut off static typing, and are then wondering why your code isn't statically typed. If you want your code to be statically typed, don't turn off static typing. – Servy Mar 31 '17 at 14:40
  • @Servy, that was the whole essence of the question -- _why_ usage of lambda expression with dynamic within it "turns off the static typing", and we found an answer in section 7.2.2 of C# specification. – Eugene D. Gubenkov Mar 31 '17 at 17:33

0 Answers0