【问题标题】:Why can't I access the model's property via the lambda expression parameter?为什么我不能通过 lambda 表达式参数访问模型的属性?
【发布时间】:2018-06-11 17:28:30
【问题描述】:

考虑一下 Razor 页面的以下代码隐藏文件。

public class IndexModel : PageModel
{
    MovieContext Context { get; }

    public IndexModel(MovieContext context)
    {
        Context = context;
    }

    public IList<Movie> Movies { get; set; }

    public async Task OnGetAsync()
    {
        Movies = await Context.Movie.ToListAsync();
    }
}

修剪后的Razor页面如下

@page
@model IndexModel
@foreach (var item in Model.Movies)
{
    @Html.DisplayFor(modelItem =>item.Title)
}

问题

仅出于学术目的,假设我被限制不能在 lambda 表达式中捕获外部变量。

为什么我不能使用

@Html.DisplayFor(modelItem => modelItem.Movies[modelItem.Movies.IndexOf(item)].Title)

而不是

@Html.DisplayFor(modelItem =>item.Title)

?

【问题讨论】:

  • 你为什么要这样做?
  • @Shyju:因为 lambda 表达式参数是框架传递的IndexModel 类型。
  • 但是您只关心打印项目的 Title 属性。仪式?为什么不使用更简单的版本。
  • @Shyju:它仅用于学术目的,为什么它不起作用。并提高我的知识。
  • 原因表达式不是代表。表达式描述代码,委托是代码

标签: c# razor lambda asp.net-core


【解决方案1】:

DisplayFor 这样的助手接受一个表达式参数。不是一个动作。它没有被执行;它被解析了。

例如,如果你写

DisplayFor( a => a.Name );

...框架只是调用a.Name 来获取值。相反,它将反映包含a.Name 的表达式,并找出引用的类型和属性。然后它查看属性的类型和属性,例如DataAnnotation 属性,以确定显示属性所需的内容。

因此,您可以提供的参数种类有限。 documentation 描述了它是如何使用的:

  • 如果属性被键入为基本类型(整数、字符串等),则该方法将呈现表示属性值的字符串。

  • 如果属性类型是布尔值,则该方法为复选框呈现 HTML 输入元素。例如,名为 Enabled 的布尔属性可能会呈现如下标记:

&lt;input class="check-box" disabled="disabled" ="checkbox" checked="checked" /&gt;

  • 如果使用数据类型属性对属性进行注释,则该属性指定为属性生成的标记。例如,如果该属性被标记为 EmailAddress 属性,则该方法会生成包含使用 mailto 协议配置的 HTML 锚点的标记,如下例所示:

&lt;a href='mailto:joe@contoso.com'&gt;joe@contoso.com&lt;/a&gt;

  • 如果对象包含多个属性,则该方法会为每个属性生成一个字符串,该字符串由属性名称的标记和属性值的标记组成。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-03-18
    • 1970-01-01
    相关资源
    最近更新 更多