c#编译的Lambda表达式访问一个对象的属性,该属性是另一个对象的属性,抛出异常
按照我之前的问题:
Lambda 表达式访问一个对象的属性,该对象是 c# 中另一个对象的属性
我现在遇到另一个问题:
var param = Expression.Parameter(typeof(GAcordos.Models.Contratos), "x");
var body = Expression.Equal(Expression.PropertyOrField(Expression.PropertyOrField(param, propName[0]), columnName.ToString()), fixedItem, false, Type.GetType("GAcordos.Helpers.Comparators").GetMethod(oper, new Type[] { propType, propType }));
var lambda = Expression.Lambda<Func<GAcordos.Models.Contratos, bool>>(body, param);
contratosList = contratosList.Where(lambda).AsQueryable();
将 lambda 传递给 Expression.Where 方法时,它不会执行我给出的替换方法到等式表达式,并执行标准 Equal 比较。
如果我编译 lambda:
contratosList = contratosList.Where(lambda.Compile()).AsQueryable();
它会抛出异常 未将对象引用设置为对象的实例。 稍后在视图中,并显示以下堆栈跟踪:
at lambda_method(Closure , Contratos )
at System.Linq.Enumerable.WhereEnumerableIterator`1.MoveNext()
at System.Linq.Buffer`1..ctor(IEnumerable`1 source)
at System.Linq.OrderedEnumerable`1.<GetEnumerator>d__0.MoveNext()
at System.Linq.Enumerable.Count[TSource](IEnumerable`1 source)
at lambda_method(Closure )
at System.Linq.EnumerableExecutor`1.Execute()
at System.Linq.EnumerableQuery`1.System.Linq.IQueryProvider.Execute[S](Expression expression)
at System.Linq.Queryable.Count[TSource](IQueryable`1 source)
at MvcContrib.Pagination.LazyPagination`1.TryExecuteQuery() in C:\Users\daniel.almeida\Downloads\MVCContrib.source\src\MVCContrib\Pagination\LazyPagination.cs:line 62
at MvcContrib.Pagination.LazyPagination`1.get_TotalItems() in C:\Users\daniel.almeida\Downloads\MVCContrib.source\src\MVCContrib\Pagination\LazyPagination.cs:line 85
at MvcContrib.UI.Pager.Pager.ToHtmlString() in C:\Users\daniel.almeida\Downloads\MVCContrib.source\src\MVCContrib\UI\Pager\Pager.cs:line 130
at MvcContrib.UI.Pager.Pager.ToString() in C:\Users\daniel.almeida\Downloads\MVCContrib.source\src\MVCContrib\UI\Pager\Pager.cs:line 125
at ASP._Page_Views_Shared_Pager_cshtml.Execute() in c:\inetpub\wwwroot\Empresas\Proactivos\GAcordos\GAcordos\Views\Shared\Pager.cshtml:line 4
at System.Web.WebPages.WebPageBase.ExecutePageHierarchy()
at System.Web.Mvc.WebViewPage.ExecutePageHierarchy()
at System.Web.WebPages.WebPageBase.ExecutePageHierarchy(WebPageContext pageContext, TextWriter writer, WebPageRenderingBase startPage)
at System.Web.Mvc.RazorView.RenderView(ViewContext viewContext, TextWriter writer, Object instance)
at System.Web.Mvc.BuildManagerCompiledView.Render(ViewContext viewContext, TextWriter writer)
at System.Web.Mvc.HtmlHelper.RenderPartialInternal(String partialViewName, ViewDataDictionary viewData, Object model, TextWriter writer, ViewEngineCollection viewEngineCollection)
at System.Web.Mvc.Html.RenderPartialExtensions.RenderPartial(HtmlHelper htmlHelper, String partialViewName, Object model)
at ASP._Page_Views_Contratos_Index_cshtml.Execute() in c:\inetpub\wwwroot\Empresas\Proactivos\GAcordos\GAcordos\Views\Contratos\Index.cshtml:line 29
at System.Web.WebPages.WebPageBase.ExecutePageHierarchy()
at System.Web.Mvc.WebViewPage.ExecutePageHierarchy()
at System.Web.WebPages.StartPage.RunPage()
at System.Web.WebPages.StartPage.ExecutePageHierarchy()
at System.Web.WebPages.WebPageBase.ExecutePageHierarchy(WebPageContext pageContext, TextWriter writer, WebPageRenderingBase startPage)
at System.Web.Mvc.RazorView.RenderView(ViewContext viewContext, TextWriter writer, Object instance)
at System.Web.Mvc.BuildManagerCompiledView.Render(ViewContext viewContext, TextWriter writer)
at System.Web.Mvc.ViewResultBase.ExecuteResult(ControllerContext context)
at System.Web.Mvc.ControllerActionInvoker.InvokeActionResult(ControllerContext controllerContext, ActionResult actionResult)
at System.Web.Mvc.ControllerActionInvoker.<>c__DisplayClass1c.<InvokeActionResultWithFilters>b__19()
at System.Web.Mvc.ControllerActionInvoker.InvokeActionResultFilter(IResultFilter filter, ResultExecutingContext preContext, Func`1 continuation)
可能出了什么问题?
Following my previous question:
Lambda expression to access a property of an object that is property of another object in c#
I have now another problem:
var param = Expression.Parameter(typeof(GAcordos.Models.Contratos), "x");
var body = Expression.Equal(Expression.PropertyOrField(Expression.PropertyOrField(param, propName[0]), columnName.ToString()), fixedItem, false, Type.GetType("GAcordos.Helpers.Comparators").GetMethod(oper, new Type[] { propType, propType }));
var lambda = Expression.Lambda<Func<GAcordos.Models.Contratos, bool>>(body, param);
contratosList = contratosList.Where(lambda).AsQueryable();
When passing the lambda to the Expression.Where method it doesn't execute the replacement method I gave to the Equal Expression, and executes the standard Equal comparison.
If I compile lambda:
contratosList = contratosList.Where(lambda.Compile()).AsQueryable();
it throws an exception Object reference not set to an instance of an object. later in the View, with the following stacktrace:
at lambda_method(Closure , Contratos )
at System.Linq.Enumerable.WhereEnumerableIterator`1.MoveNext()
at System.Linq.Buffer`1..ctor(IEnumerable`1 source)
at System.Linq.OrderedEnumerable`1.<GetEnumerator>d__0.MoveNext()
at System.Linq.Enumerable.Count[TSource](IEnumerable`1 source)
at lambda_method(Closure )
at System.Linq.EnumerableExecutor`1.Execute()
at System.Linq.EnumerableQuery`1.System.Linq.IQueryProvider.Execute[S](Expression expression)
at System.Linq.Queryable.Count[TSource](IQueryable`1 source)
at MvcContrib.Pagination.LazyPagination`1.TryExecuteQuery() in C:\Users\daniel.almeida\Downloads\MVCContrib.source\src\MVCContrib\Pagination\LazyPagination.cs:line 62
at MvcContrib.Pagination.LazyPagination`1.get_TotalItems() in C:\Users\daniel.almeida\Downloads\MVCContrib.source\src\MVCContrib\Pagination\LazyPagination.cs:line 85
at MvcContrib.UI.Pager.Pager.ToHtmlString() in C:\Users\daniel.almeida\Downloads\MVCContrib.source\src\MVCContrib\UI\Pager\Pager.cs:line 130
at MvcContrib.UI.Pager.Pager.ToString() in C:\Users\daniel.almeida\Downloads\MVCContrib.source\src\MVCContrib\UI\Pager\Pager.cs:line 125
at ASP._Page_Views_Shared_Pager_cshtml.Execute() in c:\inetpub\wwwroot\Empresas\Proactivos\GAcordos\GAcordos\Views\Shared\Pager.cshtml:line 4
at System.Web.WebPages.WebPageBase.ExecutePageHierarchy()
at System.Web.Mvc.WebViewPage.ExecutePageHierarchy()
at System.Web.WebPages.WebPageBase.ExecutePageHierarchy(WebPageContext pageContext, TextWriter writer, WebPageRenderingBase startPage)
at System.Web.Mvc.RazorView.RenderView(ViewContext viewContext, TextWriter writer, Object instance)
at System.Web.Mvc.BuildManagerCompiledView.Render(ViewContext viewContext, TextWriter writer)
at System.Web.Mvc.HtmlHelper.RenderPartialInternal(String partialViewName, ViewDataDictionary viewData, Object model, TextWriter writer, ViewEngineCollection viewEngineCollection)
at System.Web.Mvc.Html.RenderPartialExtensions.RenderPartial(HtmlHelper htmlHelper, String partialViewName, Object model)
at ASP._Page_Views_Contratos_Index_cshtml.Execute() in c:\inetpub\wwwroot\Empresas\Proactivos\GAcordos\GAcordos\Views\Contratos\Index.cshtml:line 29
at System.Web.WebPages.WebPageBase.ExecutePageHierarchy()
at System.Web.Mvc.WebViewPage.ExecutePageHierarchy()
at System.Web.WebPages.StartPage.RunPage()
at System.Web.WebPages.StartPage.ExecutePageHierarchy()
at System.Web.WebPages.WebPageBase.ExecutePageHierarchy(WebPageContext pageContext, TextWriter writer, WebPageRenderingBase startPage)
at System.Web.Mvc.RazorView.RenderView(ViewContext viewContext, TextWriter writer, Object instance)
at System.Web.Mvc.BuildManagerCompiledView.Render(ViewContext viewContext, TextWriter writer)
at System.Web.Mvc.ViewResultBase.ExecuteResult(ControllerContext context)
at System.Web.Mvc.ControllerActionInvoker.InvokeActionResult(ControllerContext controllerContext, ActionResult actionResult)
at System.Web.Mvc.ControllerActionInvoker.<>c__DisplayClass1c.<InvokeActionResultWithFilters>b__19()
at System.Web.Mvc.ControllerActionInvoker.InvokeActionResultFilter(IResultFilter filter, ResultExecutingContext preContext, Func`1 continuation)
What could be wrong?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
很难说,但如果我不得不猜测,我会说你的 GetMethod 调用返回 null。
您能否将这一行分解为临时变量并检查其值?
或者更好的是,制作一些独立的重现,供这里的人们运行。
Very hard to say but if I had to guess I would say your GetMethod call is returning null.
Can you factor out this line into a temporary variable and check its value?
Or better yet, make a little standalone repro that people here can run.
问题不在于 lambda 表达式。这是从数据库加载信息时引起的,在迭代主表查询结果时正在查询数据库中的相关表。
将 MultipleActiveResultSets=true 添加到连接字符串的提供程序部分即可解决此问题。
请参阅解决方案:
已经有一个打开的 DataReader 与此命令关联,必须先将其关闭。
The problem was not the lambda expressions. It was caused when loading info from the dababase, it was querying the database for the related tables when iterating the result of the query for the main table.
This was solved adding MultipleActiveResultSets=true to the provider part of the connection string.
See the solution for:
There is already an open DataReader associated with this Command which must be closed first.