C# 使用LINQ将具有相同值的行分组到列中

C# 使用LINQ将具有相同值的行分组到列中,c#,.net,database,linq,C#,.net,Database,Linq,我有一个LINQ查询,结果如下 Student Subject Mark Adam English 80 Adam Math 70 Adam Science 60 Moses English 95 Moses Science 75 现在我只想把它转换成下面的样子 Student English Math Science Adam 80 70 60 Moses 95

我有一个LINQ查询,结果如下

Student  Subject    Mark 
Adam     English    80
Adam     Math       70
Adam     Science    60
Moses    English    95
Moses    Science    75
现在我只想把它转换成下面的样子

Student English Math    Science
Adam    80      70      60
Moses   95              75

注意:受试者的数量不是固定的。

如果受试者已知且固定,您可以使用:

var query = db.StudentMarks
    .GroupBy(x => x.Student)
    .Select(g => new {
        Student = g.Key,
        English = g.Where(x => x.Subject == "English").Sum(x=> x.Mark),
        Math    = g.Where(x => x.Subject == "Math").Sum(x=> x.Mark),
        Science = g.Where(x => x.Subject == "Science").Sum(x=> x.Mark),
    });

如果受试者已知且固定,您可以使用:

var query = db.StudentMarks
    .GroupBy(x => x.Student)
    .Select(g => new {
        Student = g.Key,
        English = g.Where(x => x.Subject == "English").Sum(x=> x.Mark),
        Math    = g.Where(x => x.Subject == "Math").Sum(x=> x.Mark),
        Science = g.Where(x => x.Subject == "Science").Sum(x=> x.Mark),
    });
尝试这样的代码

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data;

namespace ConsoleApplication12
{
    class Program
    {
        static void Main(string[] args)
        {
            DataTable sourceTable = new DataTable();
            sourceTable.Columns.Add("Student", typeof(string));
            sourceTable.Columns.Add("Subject", typeof(string));
            sourceTable.Columns.Add("Mark", typeof(int));

            sourceTable.Rows.Add(new object[] { "Adam","English", 80});
            sourceTable.Rows.Add(new object[] { "Adam","Math", 70});
            sourceTable.Rows.Add(new object[] { "Adam","Science", 60});
            sourceTable.Rows.Add(new object[] { "Moses","English", 95});
            sourceTable.Rows.Add(new object[] { "Moses","Science", 75});

            List<string> subjects = sourceTable.AsEnumerable().Select(x => x.Field<string>("Subject")).Distinct().ToList();
            DataTable pivotTable = new DataTable();
            pivotTable.Columns.Add("Student", typeof(string));
            foreach(string subject in subjects)
            {
                pivotTable.Columns.Add(subject, typeof(int));
            }
            var students = sourceTable.AsEnumerable()
                .GroupBy(x => x.Field<string>("Student")).ToList();

            foreach (var student in students)
            {
                DataRow newRow = pivotTable.Rows.Add();
                newRow["Student"] = student.Key;
                foreach (DataRow row in student)
                {
                    newRow[row.Field<string>("Subject")] = row.Field<int>("Mark"); 
                }

            }
        }
    }
}
使用系统;
使用System.Collections.Generic;
使用System.Linq;
使用系统文本;
使用系统数据;
命名空间控制台应用程序12
{
班级计划
{
静态void Main(字符串[]参数)
{
DataTable sourceTable=新DataTable();
sourceTable.Columns.Add(“Student”,typeof(string));
sourceTable.Columns.Add(“Subject”,typeof(string));
sourceTable.Columns.Add(“Mark”,typeof(int));
添加(新对象[]{“Adam”,“English”,80});
添加(新对象[]{“Adam”,“Math”,70});
添加(新对象[]{“Adam”,“Science”,60});
添加(新对象[]{“摩西”,“英语”,95});
添加(新对象[]{“摩西”,“科学”,75});
List Subject=sourceTable.AsEnumerable().Select(x=>x.Field(“Subject”)).Distinct().ToList();
数据表数据透视表=新数据表();
数据透视表.Columns.Add(“学生”,typeof(字符串));
foreach(主题中的字符串主题)
{
数据透视表.Columns.Add(subject,typeof(int));
}
var students=sourceTable.AsEnumerable()
.GroupBy(x=>x.Field(“学生”)).ToList();
foreach(学生中的var学生)
{
DataRow newRow=数据透视表.Rows.Add();
newRow[“Student”]=Student.Key;
foreach(学生中的数据行)
{
新行[行字段(“主题”)]=行字段(“标记”);
}
}
}
}
}

尝试这样的代码

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data;

namespace ConsoleApplication12
{
    class Program
    {
        static void Main(string[] args)
        {
            DataTable sourceTable = new DataTable();
            sourceTable.Columns.Add("Student", typeof(string));
            sourceTable.Columns.Add("Subject", typeof(string));
            sourceTable.Columns.Add("Mark", typeof(int));

            sourceTable.Rows.Add(new object[] { "Adam","English", 80});
            sourceTable.Rows.Add(new object[] { "Adam","Math", 70});
            sourceTable.Rows.Add(new object[] { "Adam","Science", 60});
            sourceTable.Rows.Add(new object[] { "Moses","English", 95});
            sourceTable.Rows.Add(new object[] { "Moses","Science", 75});

            List<string> subjects = sourceTable.AsEnumerable().Select(x => x.Field<string>("Subject")).Distinct().ToList();
            DataTable pivotTable = new DataTable();
            pivotTable.Columns.Add("Student", typeof(string));
            foreach(string subject in subjects)
            {
                pivotTable.Columns.Add(subject, typeof(int));
            }
            var students = sourceTable.AsEnumerable()
                .GroupBy(x => x.Field<string>("Student")).ToList();

            foreach (var student in students)
            {
                DataRow newRow = pivotTable.Rows.Add();
                newRow["Student"] = student.Key;
                foreach (DataRow row in student)
                {
                    newRow[row.Field<string>("Subject")] = row.Field<int>("Mark"); 
                }

            }
        }
    }
}
使用系统;
使用System.Collections.Generic;
使用System.Linq;
使用系统文本;
使用系统数据;
命名空间控制台应用程序12
{
班级计划
{
静态void Main(字符串[]参数)
{
DataTable sourceTable=新DataTable();
sourceTable.Columns.Add(“Student”,typeof(string));
sourceTable.Columns.Add(“Subject”,typeof(string));
sourceTable.Columns.Add(“Mark”,typeof(int));
添加(新对象[]{“Adam”,“English”,80});
添加(新对象[]{“Adam”,“Math”,70});
添加(新对象[]{“Adam”,“Science”,60});
添加(新对象[]{“摩西”,“英语”,95});
添加(新对象[]{“摩西”,“科学”,75});
List Subject=sourceTable.AsEnumerable().Select(x=>x.Field(“Subject”)).Distinct().ToList();
数据表数据透视表=新数据表();
数据透视表.Columns.Add(“学生”,typeof(字符串));
foreach(主题中的字符串主题)
{
数据透视表.Columns.Add(subject,typeof(int));
}
var students=sourceTable.AsEnumerable()
.GroupBy(x=>x.Field(“学生”)).ToList();
foreach(学生中的var学生)
{
DataRow newRow=数据透视表.Rows.Add();
newRow[“Student”]=Student.Key;
foreach(学生中的数据行)
{
新行[行字段(“主题”)]=行字段(“标记”);
}
}
}
}
}

如果您不知道将有多少主题,您可以将信息整理到嵌套字典中,如下所示:

var subjectMarksByStudent = new Dictionary<string, Dictionary<string, int>>();
foreach (var studentMark in studentMarks)
{
    Dictionary<string, int> subjectsAndMarksForStudent;
    if (subjectMarksByStudent.TryGetValue(studentMark.Name, out subjectsAndMarksForStudent))
    {
        subjectsAndMarksForStudent.Add(studentMark.Subject, studentMark.Mark);
    }
    else
    {
        subjectMarksByStudent.Add(studentMark.Name, new Dictionary<string, int> {{ studentMark.Subject, studentMark.Mark }});
    }
} 
var subjectMarksByStudent=newdictionary();
foreach(学生分数中的var studentMark)
{
词典主题和学生标记;
if(subjectMarksByStudent.TryGetValue(studentMark.Name、out subjects和marksforstudent))
{
添加(studentMark.Subject,studentMark.Mark);
}
其他的
{
subjectMarksByStudent.Add(studentMark.Name,新字典{{{studentMark.Subject,studentMark.Mark}});
}
} 

如果您不知道将有多少主题,您可以将信息整理到嵌套字典中,如下所示:

var subjectMarksByStudent = new Dictionary<string, Dictionary<string, int>>();
foreach (var studentMark in studentMarks)
{
    Dictionary<string, int> subjectsAndMarksForStudent;
    if (subjectMarksByStudent.TryGetValue(studentMark.Name, out subjectsAndMarksForStudent))
    {
        subjectsAndMarksForStudent.Add(studentMark.Subject, studentMark.Mark);
    }
    else
    {
        subjectMarksByStudent.Add(studentMark.Name, new Dictionary<string, int> {{ studentMark.Subject, studentMark.Mark }});
    }
} 
var subjectMarksByStudent=newdictionary();
foreach(学生分数中的var studentMark)
{
词典主题和学生标记;
if(subjectMarksByStudent.TryGetValue(studentMark.Name、out subjects和marksforstudent))
{
添加(studentMark.Subject,studentMark.Mark);
}
其他的
{
subjectMarksByStudent.Add(studentMark.Name,新字典{{{studentMark.Subject,studentMark.Mark}});
}
} 

你赢了我+1主题的数量不是固定的。@Parvezmr罗宾:在sql server中没有真正的运算符。您可以尝试这样的方法:我会在存储过程、表值函数或视图中执行这些操作。然后你可以用LINQ查询这些函数/视图。你比我快+1主题的数量不是固定的。@Parvezmr罗宾:在sql server中没有真正的运算符。您可以尝试这样的方法:我会在存储过程、表值函数或视图中执行这些操作。然后可以使用LINQ查询这些函数/视图。如果主题不固定,则结果不能是具有属性的类。那么你期望它是什么呢?提供更多的代码或者解释你想对结果做什么,或者你面临什么问题。如果主题不固定,那么结果就不能是一个具有属性的类。那么你期望它是什么呢?提供更多的代码或者解释你想对结果做什么或者你面临什么问题。