【问题标题】:Dynamic LINQ cast to nullable动态 LINQ 强制转换为可为空
【发布时间】:2014-02-18 04:25:54
【问题描述】:

我正在使用带有 NHibernate 的动态 LINQ。 简单的例子说明了我的问题:

var q = sess.Query<User>().Select("new (Id, Login, Person.Id as PersonId)");

当 User.Person == null 的数据库中的用户在哪里时抛出 NullReferenceException。

这样就解决了问题:

var q = sess.Query<User>().Select(new { Id, Login, PersonId = (long?)Person.Id });

但我需要类似的东西

var q = sess.Query<User>().Select("new (Id, Login, (long?)Person.Id as PersonId)");

因为选择表达式是动态生成的。 不幸的是,动态 LINQ 不理解强制转换为 (long?) :(

我应该怎么做? 提前致谢!

==== 编辑 ====

好的,我明白了两件事: 1.动态LINQ不知道long,只知道Int64。 2. Cast 不是 '(Int64)something' 而是 'Int64(something)'。 所以整个我的代码应该是

sess.Query<User>().Select("new (Id, Login, Int64?(Person.Id) as PersonId)");

但它仍然不能解决我的整个问题,因为 NHibernate 现在失败,出现无法执行查询 [SQL: SQL 不可用] 异常和 NullReference 内部异常。

【问题讨论】:

  • 为什么你在动态 linq 代码中尝试 Person.Id,但在简单 linq 中你使用 (long?)PersonId
  • 你试试var q = sess.Query&lt;User&gt;().Select("new (Id, Login, PersonId )");
  • 抱歉,输入错误,正确的是 var q = sess.Query().Select(new { Id, Login, PersonId = (long?)Person.Id });
  • 您能提供UserPerson 类的样本吗? Person 也可以为空吗?
  • 示例:class User { public long Id {get;set;} public string Login {get;set;} public Person Person {get;set;} }

标签: c# linq nhibernate linq-to-nhibernate dynamic-linq


【解决方案1】:

我终于掌握了这个问题。我研究了 Dynamic.cs,发现 Dynamic LINQ 的语法非常具体。特别是字符串表达式“SomeType(SomeExpression)”仅在 SomeType 没有带有一个参数的构造函数时才生成强制转换表达式。在其他情况下,它会生成“new SomeType(SomeExpression)”。我认为这是一个错误,并稍微修改了 Dynamic.cs。

现在在我的示例中,演员表可以设为 'Int64?人.Id'。这不是“正常”的强制转换语法,但它对我来说就像一种魅力。 Dynamic ExpressionParser 非常好,但不幸的是它不能很好地适应 C# 强制转换语法。

我还在 Dynamic.cs 中注册了短类型名称,例如“long”、“int”等。

修改后的源码可以在这里下载:http://1drv.ms/1cRJtSP

【讨论】:

  • 谢谢!!!我区分了您提供的源代码,并根据所需的实际更改编辑了您的答案。我使用的是 Dynamic Linq 的修改版本,所以我需要手动进行更改。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多