SELECT语句中的Linq静态方法

时间:2012-12-21 07:49:24

标签: c# entity-framework linq-to-entities linq-to-objects

我正在与EF合作并提出一些疑问。这是我的代码

IEnumerable<Customer> customers = from c in context.Customers 
    select new Customer
    {
        ID = c.ID,
        Name = c.Name,
        LastName = c.LastName,
        DepID = c.DepID,
        Editable = SomeStruct.Check(c.DepID)
    }

public struct SomeStruct
{
    public static bool Check(int depID)
    {
        //Here I have some logic
    }
}

工作正常。 但是,如果我将SomeStruct声明为class,则会失败。

我的问题是:

  1. 为什么会这样?
  2. 使用静态函数是否强制查询执行?

3 个答案:

答案 0 :(得分:6)

在您的代码方法中,SomeStruct.Check(c.DepID)应该转换为SQL查询。这描述了类/结构的行为等。这是由于Entity Framework在类和结构中使用这些方法的不同工作。但你可以在客户端进行检查:

IEnumerable<Customer> customers = from c in context.Customers 
    select new
    {
        ID = c.ID,
        Name = c.Name,
        LastName = c.LastName,
        DepID = c.DepID
    }
    .AsEnumerable()
    .Select(d=>new Customer
    {
        ID = c.ID,
        Name = c.Name,
        LastName = c.LastName,
        DepID = c.DepID,
        Editable = SomeStruct.Check(c.DepID)
    });

或者您可以将Editable属性设置为readonly属性:

public class Customer{
    public int ID{get;set;}
    public string Name{get;set;}
    public string LastName {get;set;}
    public Guid DepID{get;set;}
    public bool Editable{get{return SomeStruct.Check(DepID);}}
}

答案 1 :(得分:1)

您的代码无法与linq一起使用,这很容易重现。无法转换为sql的任何将引发运行时异常。在你的情况下:

  

NotSupportedException:LINQ to Entities无法识别方法'Boolean Check(Int32)'方法,并且此方法无法转换为商店表达式。

如果您在某个时刻开始运行,这与structclass差异无关,请参阅What's the difference between a static struct method and a static class method?

您可能同时更改了其他内容,例如在ToList()之前添加select

答案 2 :(得分:0)

假设这是一个运行时问题,在您描述的许多情况下,这是一个参考问题。 EF的linq提供程序支持调用类中声明的静态方法(静态或非静态)。

  1. 我建议您将结构更改为类并将其设置为静态以帮助您调查此问题。

  2. 不会,在您调用第一次迭代或客户之前不会执行任何操作。

  3. 希望这有帮助