【问题标题】:How to convert/cast IQueryable<AnonymousType> to IQueriable<Strong Typed Object> with lambda expressions如何使用 lambda 表达式将 IQueryable<Anonymous Type> 转换/转换为 IQueryable<Strongly Typed Object>
【发布时间】:2014-12-14 10:07:51
【问题描述】:

这是我想要达到的目标:

 int id = 1;
        var db = new Project.Models.Context();
        var query1 = db.Users.Where(t => t.id == id);
        //here is where the problem starts
        IQueryable<Project.Models.test> test = query1.Join(db.Table2,
                    users => users.id,
                    table2 => table2.userId,
                    (users, table2) => new
                    {
                        users.UserName,
                        table2.SomeValue
                    });

到目前为止我已经尝试过:

-将 query1 转换为

(IQueryable<Project.Models.test>)query1

-在关键字 new 处添加强类型名称:

 (users, table2) => new IQueryable<Project.Models.test>) ...

 (users, table2) => new Project.Models.test ...

-命名列 (用户,表 2)=> 新 { ColumnName1 = users.UserName, ColumnName2 = table2.SomeValue });

-以上的组合

我也明白有一种方法可以使用普通的 sql 表达式来解决这个问题:

 select new Project.Models.test 
        {
            ColumnName1 = users.UserName,
            ColumnName2 = table2.SomeValue
        }    

但如果可能的话,我想用 lambda 表达式来写这个。

我是第一次发帖,也是长期读者,希望一切都写得正确而清晰。

ps:我还冒昧地简化了变量名和连接查询。

编辑:

为了完整起见: 将查询保存在匿名变量 joinTable 中,然后执行“插入”语句。

IQueryable<Project.Models.test> tst = from a in joinedTable
                                      select new Project.Models.test
                                      {
                                          UserName = a.UserName,
                                          SomeValue = a.SomeValue
                                      };

因此,如果可以使用 lambda 表达式编写上述语句,则将是一个子问题。

【问题讨论】:

  • 这种方式是唯一的方式。没有办法投射。
  • 我不和你在一起 - 匿名加入投影 - (users, table2) =&gt; new {...} 和强类型 (users, table2) =&gt; new Project.Models.test {...} 都使用 lambdas。后者不需要强制转换,因为它已经是给定的类型? (即使 anon 类与 Strong POCO 具有完全相同的形状,也不能直接将其转换为它 AFAIK)
  • 当您尝试您的选项(users, table2) =&gt; new Project.Models.test(){ ColumnName1 = users.UserName, ColumnName2 = table2.SomeValue } 时,什么不起作用?你得到什么错误? Project.Models.test 是 sql 数据类型还是在 sql 端没有对应等价物的自定义类?在后一种情况下,可能无法在 sql join 中使用它。
  • 现在可以使用了!我打错了一个列名。现在我可以将我所有的查询都变成 lambda 形式了。

标签: c# linq casting lambda iqueryable


【解决方案1】:

这是你的意思吗?

    IQueryable<Project.Models.test> query =
        from u in db.Users
        join t in db.Table2 on u.id equals t.userId
        where u.id == id
        select new Project.Models.test  
                {
                    UserName = u.UserName,
                    SomeValue = t.SomeValue
                };

【讨论】:

  • 在某种程度上是的,但如果可能的话,我想用 lambda 表示法写这个表达式。
【解决方案2】:

我认为这是不可能的。你可以这样做

result.AsEnumerable().Select(anonymous => new Typed { Property = anonymous.Property));

但这非常难看。我也会尝试使用 dotPeek 查看生成的代码。

【讨论】:

    【解决方案3】:

    答案是:

    int id = 1;
        var db = new Project.Models.Context();
        var query1 = db.Users.Where(t => t.id == id);
        //here is where the problem starts
        IQueryable<Project.Models.test> test = query1.Join(db.Table2,
                    users => users.id,
                    table2 => table2.userId,
                    (users, table2) => new Project.Models.test()
                    {
                        columName1 = users.UserName,
                        columName2 = table2.SomeValue
                    });
    

    ColumnNames 必须与 new Project.Models.test() 中的属性相对应。

    感谢 HugoRune 让我重新检查我的代码。我还想指出,Jaap Elgersma anwser 也解决了这个问题,但不是用 lambda 表示法。

    【讨论】:

      猜你喜欢
      • 2020-04-23
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-02-07
      • 1970-01-01
      • 2020-01-10
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多