ASP.NET MVC 3 Razor递归功能


76

好的,所以我想显示一个包含列表列表的列表...

我无法知道要显示多少个级别,因此我认为这是我打破旧的递归例程的地方。

我在确切地如何解决这个问题上遇到了麻烦。

这是我到目前为止(鉴于-简化):

@foreach(MyObject item in @Model.ListOfObjects){ 
    <div> @item.Title </div>
    //Call recursive function?
}

现在,这些对象中的每一个也都有一个List <MyObject>。我想显示此div以下的每个级别,例如每个级别都有一个缩进标签。

我本来想在这里使用Razor函数,但是在构建它时需要一些帮助。这是我的想法:

@functions{
    public static void ShowSubItems(MyObject _object){
         if(_object.ListOfObjects.Count>0){
             foreach(MyObject subItem in _object.listOfObjects){

                 // Show subItem in HTML
                 ShowSubItems(subItem);
             }
         }
     }
 }

但是如您所见,我显然需要一些帮助:)

Answers:


204

Razor视图引擎允许使用@helper关键字编写内联递归帮助器。

@helper ShowTree(IEnumerable<Foo> foos)
{
    <ul>
        @foreach (var foo in foos)
        {
            <li>
                @foo.Title
                @if (foo.Children.Any())
                {
                    @ShowTree(foo.Children)
                }
            </li>
        }
    </ul>
}

5
还剩下一件事,它必须调用@ShowTree(Foos)
vicky

1
这真的很好。提及stackoverflow.com/questions/12943245/…来引用cshtml页面上的局部变量也可能是有意义的。
特拉维斯J

如何在asp.net core 2中实现此代码?在asp.net核心2中,没有@helper
鲁道拉

2
@Jahan看起来@helper已经在ASP.NET Core中消失了。内联函数是一种潜在的替代方法:github.com/aspnet/Razor/issues/715#issuecomment-272890766,但可读性却差很多!
Paolo Moretti

@PaoloMoretti当我将其定义为递归Func时,该怎么办?我想使用递归功能创建嵌套注释。此错误在VS2018 IDE中显示:“未分配的局部变量'FunctionName'的使用可能在访问前未初始化”>
Roohullah Allem说

13

我认为最好为此创建一个HTML帮助器。像这样:

public static string ShowSubItems(this HtmlHelper helper, MyObject _object)
{
     StringBuilder output = new StringBuilder();
     if(_object.ListOfObjects.Count > 0)
     {
         output.Append("<ul>");

         foreach(MyObject subItem in _object.listOfObjects)
         {
             output.Append("<li>");
             output.Append(_object.Title);
             output.Append(html.ShowSubItems(subItem.listOfObjects);
             output.Append("</li>")
         }
         output.Append("</ul>");
     }
     return output.ToString();
}

然后这样称呼它:

@foreach(MyObject item in @Model.ListOfObjects){
    <div> @item.Title </div>
    @html.ShowSubItems(item)
}
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.