form 利用BeginCollectionItem提交集合List<T>数据 以及提交的集合中含有集合的数据类型 如List<List<T>> 数据的解决方案

例子:

 public class IssArgs
    {
        public List<IssTabArgs> Tabs { get; set; }
    }

    public class IssTabArgs
    {
        public int Num { get; set; }

        public string Tab { get; set; }

        public List<IssArg> Args { get; set; }
    }

    public class IssArg
    {
        public int Num { get; set; }

        public string Name { get; set; }

        public string Value { get; set; }
    }

现在需要上传这样的数据

 @using (Html.BeginForm("SaveGpIss", "Issue"))
    {

                      @foreach (var item in Model.TabArgs.Tabs)
                        {
                            @Html.Partial("_ArgsTabPar",item)
                        }


     }
@model Web.Models.Vm.Issue.IssTabArgs

    <tbody>
    @using (Html.BeginCollectionItem("TabArgs.Tabs"))
    {
        @Html.HiddenFor(m => m.Num, new { @class = "arg_tab_num" })
        <tr class="un">
            <td colspan="2" class="w">@Html.EditorFor(m=>m.Tab, new { HtmlAttributes = new { PlaceHolder = "表名称" } })</td>
        </tr>
        foreach (var item in Model.Args)
        {
            @Html.Partial("_ArgPar",item)
        }
    }
    </tbody>

下面是第级集合的重点

@model Web.Models.Vm.Issue.IssArg

@{
    var colId = ViewData.TemplateInfo.HtmlFieldPrefix;
}
<tr>
    @using (Html.BeginCollectionItem(colId + ".Args"))
    {
        @Html.HiddenFor(m=>m.Num,new {@class="arg_num"})
        <td class="n">@Html.EditorFor(m => m.Name, new { HtmlAttributes = new { PlaceHolder = "参数名称" } })</td>
        <td class="i">@Html.EditorFor(m => m.Value, new { HtmlAttributes = new { PlaceHolder = "参数值" } })</td>
    }
</tr>
ViewData.TemplateInfo.HtmlFieldPrefix;
BeginCollectionItem 反编译代码,将 Guid.NewGuid().ToString() 值储存 ViewData.TemplateInfo.HtmlFieldPrefix;
 
using System;
using System.Collections.Generic;
using System.IO;
using System.Web;
using System.Web.Mvc;

namespace HtmlHelpers.BeginCollectionItem
{
  public static class HtmlPrefixScopeExtensions
  {
    private const string IdsToReuseKey = "__htmlPrefixScopeExtensions_IdsToReuse_";

    public static IDisposable BeginCollectionItem(this HtmlHelper html, string collectionName)
    {
      return html.BeginCollectionItem(collectionName, html.ViewContext.Writer);
    }

    public static IDisposable BeginCollectionItem(this HtmlHelper html, string collectionName, TextWriter writer)
    {
      Queue<string> idsToReuse = HtmlPrefixScopeExtensions.GetIdsToReuse(html.ViewContext.get_HttpContext(), collectionName);
      string str = idsToReuse.Count > 0 ? idsToReuse.Dequeue() : Guid.NewGuid().ToString();
      writer.WriteLine("<input type="hidden" name="{0}.index" autocomplete="off" value="{1}" />", (object) collectionName, (object) html.Encode(str));
      return html.BeginHtmlFieldPrefixScope(string.Format("{0}[{1}]", (object) collectionName, (object) str));
    }

    public static IDisposable BeginHtmlFieldPrefixScope(this HtmlHelper html, string htmlFieldPrefix)
    {
      return (IDisposable) new HtmlPrefixScopeExtensions.HtmlFieldPrefixScope(html.ViewData.TemplateInfo, htmlFieldPrefix);
    }

    private static Queue<string> GetIdsToReuse(HttpContextBase httpContext, string collectionName)
    {
      string str1 = "__htmlPrefixScopeExtensions_IdsToReuse_" + collectionName;
      Queue<string> stringQueue = (Queue<string>) httpContext.Items[(object) str1];
      if (stringQueue == null)
      {
        httpContext.Items[(object) str1] = (object) (stringQueue = new Queue<string>());
        string str2 = httpContext.Request[collectionName + ".index"];
        if (!string.IsNullOrEmpty(str2))
        {
          string str3 = str2;
          char[] chArray = new char[1]{ ',' };
          foreach (string str4 in str3.Split(chArray))
            stringQueue.Enqueue(str4);
        }
      }
      return stringQueue;
    }

    internal class HtmlFieldPrefixScope : IDisposable
    {
      internal readonly TemplateInfo TemplateInfo;
      internal readonly string PreviousHtmlFieldPrefix;

      public HtmlFieldPrefixScope(TemplateInfo templateInfo, string htmlFieldPrefix)
      {
        this.TemplateInfo = templateInfo;
        this.PreviousHtmlFieldPrefix = this.TemplateInfo.HtmlFieldPrefix;
        this.TemplateInfo.HtmlFieldPrefix = htmlFieldPrefix;
      }

      public void Dispose()
      {
        this.TemplateInfo.HtmlFieldPrefix = this.PreviousHtmlFieldPrefix;
      }
    }
  }
}

还有一种解决方式就是通过脚本的方式改变input name 的内容,这里不多说了

原文地址:https://www.cnblogs.com/hanstar/p/6786411.html