C# - 将列表拆分为n个子列表

nor*_*att 4 c# linq

我想将列表拆分为'n'个子列表.

我有一份表格老师名单和一份学生名单.每个学生都被分配到一个表格教师,每个表格教师可以有一个以上的学生.表单教师列表是动态的 - 它是根据表单上的复选框选择填充的(即:列表中可能有一个,三个,六个等).

//A method to assign the Selected Form teachers to the Students
private void AssignFormTeachers(List<FormTeacher> formTeacherList, List<Student> studentList)
{
    int numFormTeachers = formTeacherList.Count;

    //Sort the Students by Course - this ensures cohort identity.
    studentList = studentList.OrderBy(Student => Student.CourseID).ToList();

    //Split the list according to the number of Form teachers
    List<List<Student>> splitStudentList = splitList(numFormTeachers , studentList);
Run Code Online (Sandbox Code Playgroud)

splitList()方法是在那里我试图名单分成学生列出的清单,但我有一个问题.假设有3名表格教师 - 我似乎无法将列表分成3个子列表,而是最终得到3个学生的列表.

我真的很感激这方面的一些帮助.我已经搜索了一个可能的解决方案,但每次我都会得到大小为'n'的列表,而不是'n'个列表.如果之前已经回答过这个问题,请指出我的答案.

Mar*_*zek 15

您是否尝试将列表划分为n具有相同数量元素的部分?

试试GroupBy:

var splitStudentList = studentList.Select((s, i) => new { s, i })
                                  .GroupBy(x => x.i % numFormTeachers)
                                  .Select(g => g.Select(x => x.s).ToList())
                                  .ToList();
Run Code Online (Sandbox Code Playgroud)

或者您可以创建自己的扩展方法来执行此操作.我已经在我的博客上描述了如何做到这一点:使用LINQ对集合进行分区:不同的方法,不同的性能,相同的结果.

public IEnumerable<IEnumerable<T>> Partition<T>(IEnumerable<T> source, int size)
{
    var partition = new List<T>(size);
    var counter = 0;

    using (var enumerator = source.GetEnumerator())
    {
        while (enumerator.MoveNext())
        {
            partition.Add(enumerator.Current);
            counter++;
            if (counter % size == 0)
            {
                yield return partition.ToList();
                partition.Clear();
                counter = 0;
            }
        }

        if (counter != 0)
            yield return partition;
    }
}
Run Code Online (Sandbox Code Playgroud)

用法:

var splitStudentList = studentList.Partition(numFormTeachers)
                                  .Select(x => x.ToList())
                                  .ToList();
Run Code Online (Sandbox Code Playgroud)