如何评估lambda表达式以确定对象类型

时间:2013-11-15 01:49:27

标签: c# lambda expression

public class Tomato
{}
public class Potato
{}
public class UIPotatoBinding(Expression<Func<object>> expression)
{
    // What to put here to make sure lambda results in Potato(s)
}     
public class UITomatoBinding(Expression<Func<object>> expression)
{
    // What code do I need to put here to determine if the lambda expression being passed in
    // results in Tomato, List<Tomato>, IEnumerable<Tomato>, ObservableCollection<Tomato>
    // TomatoCollection, or some other Tomato related Linq construct.
}

这个lambda的东西对我来说仍然很陌生。如果我问的是已经在别处已经回答的明显问题,我道歉。

2 个答案:

答案 0 :(得分:3)

回应你的评论

I need to be able to handle List<Tomato>, IEnumerable<Tomato>, ObservableCollection<Tomato>, Tomato, TomatoCollection

前三个(可能是最后一个)可以在IEnumerable<Tomato>中恢复。

如果在这些中混合使用返回Tomato的lambda,我觉得没什么意义,可能你会更适合重载方法。

所以:

 public class MyProduce(Func<IEnumerable<Tomato>> expression)   // No need to make it an expression, so you allow for an already compiled lambda to be used.

如果您想添加Tomato

 public class MyProduce(Func<Tomato> expression) {
      Func<IEnumerable<Tomato>> expression2 = () => ( new Tomato[] { expression() });
      // Here you use expression2 as in the previous constructor.
 }

如果要将Potato添加到混合中,可以使该类成为通用类,也可以创建两个类共有的超类/接口。

底线是:让你的先决条件更强大

如果您允许您的代码接收任何内容,您将无法对您正在处理的内容做出有效的假设,并且您的代码将以很多spaggetti结束。允许传递object并希望你的代码处理它是禁止你使用语言提供给你的设施(你可以用Javascript写,值得)。

答案 1 :(得分:2)

这是一个做你想做的事的例子。如果你有它,将在linqpad中运行。

void Main()
{
    Expression<Func<object>> f = () => new Potato();
    Helper.MyProduce(f);
}


public class Tomato 
{}
public class Potato
{}

public static class Helper
{
    public static void MyProduce(Expression<Func<object>> expression)
    {
        var func = expression.Compile();
        var result = func();

        if(result is Tomato)
            Console.Write("Tomato");
        else if (result is Potato)
            Console.Write("Potato");
        else
            Console.Write("Unknown");
    }
}