0

私は次のように再帰的(親、子)の関係を持っているモデルと呼ばれるカテゴリーがあります次のように私も親グループを選択することができ、親子関係に基づいて - 基本的に私は親から子供をインデントする:次のようにASP MVC 5 C#再帰木へのグループとのインデントA DropDownListの

<select name="Category" id="Category"> 
     <option value="0">All</option> 
     <option value="1">Cars</option> 
     <option value="2">--Toyota</option> 
     <option value="3">--Nissan</option> 
     <option value="4">Fruits</option> 
     <option value="5">--Apples</option> 
     <option value="6">--Oranges</option> 
    </select> 

私の表のデータは、次のとおりです。

Id | ParentId | Name 
---------------------- 
1 | null | Cars 
2 | 1  | Toyota 
3 | 1  | Nissan 
4 | null | Fruits 
5 | 4  | Apples 
6 | 4  | Oranges 

現在、私は以下のLINQクエリを持っていますが、単純に通常のドロップダウンリストを生成します。私はそれがHtml.DropDownListForを使用してレンダリングだときのためにそれらを正しくグループ化し、インデントを取得するためにLINQクエリを修正するにはどうすればよい

public IEnumerable<SelectListItem> GetCategoriesSelectList() 
    { 
     var categories = new List<SelectListItem> 
      { 
       new SelectListItem() {Value = "0", Text = "All" } 

      }.Concat(_context.Category.Select(x => new SelectListItem 
      { 
       Value = x.Id.ToString(), 
       Text = x.Name 
      }).OrderBy(x => x.Value).ToList()); 

     return categories 
    } 

私は元の選択リストを次のようにいくつかの種類のツリーを達成するために修正しようとしましたが、私はEnumerateNodesメソッドに固執しています。下の原稿は、私が次のサイトhttp://www.codeproject.com/Articles/23949/Building-Trees-from-Lists-in-NETから引っ張ったulリストを印刷するためのものです。どのようにそれを反復して各アイテムを返すのですか?その子が--を子リストに追加して追加する場合はどうすればいいですか?

public IEnumerable<SelectListItem> GetCategoriesSelectList() 
    { 
     IList<Category> listOfNodes = GetListOfNodes(); 
     IList<Category> topLevelCategories = TreeHelper.ConvertTOForest(listOfNodes); 

     var cats = new List<SelectListItem> 
     { 
      new SelectListItem { Value = "0", Text = "All"} 
     }; 

     foreach(var category in topLevelCategories) { 
      var catName = EnumerateNodes(category); 
      cats.Add(new SelectListItem { Value = category.Id.ToString(), Text = catName }); 
     } 
     return cats; 
    } 

    private List<Category> GetListOfNodes() 
    { 

    List<Category> sourceCategories = _context.Category.ToList(); 
    List<Category> categories = new List<Category>(); 
    foreach (Category sourceCategory in sourceCategories) 
    { 
     Category s = new Category(); 
     s.Id = sourceCategory.Id; 
     s.Name = sourceCategory.Name; 
     if (sourceCategory.ParentId != null) 
     { 
      s.Parent = new Category(); 
      s.Parent.Id = (int)sourceCategory.ParentId; 
     } 
     categories.Add(s); 
    } 
    return categories; 
    } 

private static string EnumerateNodes(Category parent) 
{ 
    if (category.Children.Count > 0) { 
     Response.Write("<ul>"); 
     foreach(Category child in category.Children) { 
      EnumerateNodes(child); 
     } 
     Response.Write("</ul>"); 
    } 
    Response.Write("</li>"); 
} 
+0

ここで、正確にスタックされますか。ドロップダウンリストを作成する方法を知りたい場合は、[ASP.Net MVCでDropDownListを使用するための最良のプログラミング方法](http://stackoverflow.com/a/37819577/296861)を参照してください。 – Win

+0

@win私はリストを作成する方法を知っています.LINQをグループ化してインデントする方法を書いています。 – adam78

+1

[親子関係C#を再帰的にチェックしてツリータイプリストを作成する]の可能な複製(http://stackoverflow.com/questions/15867478/build-tree-type-list-by-recursively-checking-parent-child-relationship -c-sharp) – Win

答えて

0

あなたはまず、親カテゴリを選択(ParentIdnullです)、その後、各親カテゴリのために、その子カテゴリを選択することができます。

public IEnumerable<SelectListItem> GetCategoriesSelectList() 
{ 
    var categories = _context.Category.ToList(); 
    // Initialise list and add first "All" item 
    List<SelectListItem> options = new List<SelectListItem> 
    { 
     new SelectListItem(){ Value = "0", Text = "All" } 
    }; 
    // Get the top level parents 
    var parents = categories.Where(x => x.ParentId == null); 
    foreach (var parent in parents) 
    { 
     // Add SelectListItem for the parent 
     options.Add(new SelectListItem() 
     { 
      Value = parent.Id.ToString(), 
      Text = parent.Name 
     }); 
     // Get the child items associated with the parent 
     var children = categories.Where(x => x.ParentId == parent.Id); 
     // Add SelectListItem for each child 
     foreach (var child in children) 
     { 
      options.Add(new SelectListItem() 
      { 
       Value = child.Id.ToString(), 
       Text = string.Format("--{0}",child.Name) 
      }); 
     } 
    } 
    return options; 
} 
+0

次の行 'foreach(子のvar子) 'に'このコマンドに関連付けられている開いているDataReaderが既にあります.'というエラーが発生しました。修正するために、 'var categories = _context.Category;'を 'var categories = _context.Category.ToList()'に変更しました。また、 'var children = products.Where(x => x.ParentId == parent.Id);'これは 'var children = categories.Where(x => x.ParentId == parent)でなければなりません。あなたがあなたの答えを修正したら、それを解決策としてマークすることができます。乾杯。 – adam78

+0

今すぐ更新しました。 :) –

関連する問題