我有一个表(如数字列表中),通过一系列linq查询重新创建。我正在尝试根据第一行中的值按降序对列进行排序。
我的数据库看起来像这样:
Data
{
ColumnLabel,
RowLabel,
Value
}
{"Cat", "All", 9}
{"Dog","All", 17}
{"Fish", "All", 4}
{"Cat", "Girls", 3}
{"Dog","Girls", 2}
{"Fish", "Girls", 2}
{"Cat", "Boys", 6}
{"Dog","Boys", 15}
{"Fish", "Boys", 2}
当我天真地将这张桌子加在一起时,它看起来像这样:
Cat | Dog | Fish
All 9 17 4
Girls 3 15 2
Boys 6 2 2
我想要做的是根据ColumnLabels
Value
的降序对RowLabel == "All"
进行排序。我希望表格的样子是这样的:
Dog | Cat | Fish
All 17 9 4
Girls 15 3 2
Boys 2 6 2
注意狗和猫的行被翻转。
我需要使用HTML输出这个表,所以我遍历每一行。
我首先对ColumnLabels
:
var top = data.Where(x => x.RowLabel ==“All”) .OrderBy(x => x.Data) .Select(x => x.ColumnLabel).SingleOrDefault();
现在top
包含我希望列显示的顺序; {Dog, Cat, Fish}
。我并不关心行如何垂直排序。
我当时想要做的是根据它的RowLabel
值对每一行进行分组:
var row = data.GroupBy(x => x.RowLabel)
.OrderBy(y => ??????????????);
//I want to OrderBy the values in top
//How do I do this?
然后我遍历每一行并创建我的HTML表格。这部分很简单,但我不知道如何根据最高顺序订购后续行。我如何在LINQ中执行此操作?
答案 0 :(得分:2)
我相信这会做你想要的:
var order = data
.Where(x => x.RowLabel == "All")
.OrderByDescending(x => x.Value)
.Select((x, i) => new { x, i })
.ToDictionary(x => x.x.ColumnLabel, x => x.i);
var result = data
.GroupBy(x => x.RowLabel, (x, y) => y.OrderBy(z => order[z.ColumnLabel]));
foreach (var x in result)
{
foreach (var y in x)
{
Console.WriteLine("ColumnLabel: {0}, RowLabel: {1}, Value: {2}", y.ColumnLabel, y.RowLabel, y.Value);
}
}
结果:
ColumnLabel: Dog, RowLabel: All, Value: 17
ColumnLabel: Cat, RowLabel: All, Value: 9
ColumnLabel: Fish, RowLabel: All, Value: 4
ColumnLabel: Dog, RowLabel: Girls, Value: 2
ColumnLabel: Cat, RowLabel: Girls, Value: 3
ColumnLabel: Fish, RowLabel: Girls, Value: 2
ColumnLabel: Dog, RowLabel: Boys, Value: 15
ColumnLabel: Cat, RowLabel: Boys, Value: 6
ColumnLabel: Fish, RowLabel: Boys, Value: 2
如果我误解了你的问题,请告诉我,但这里的想法是创建一个字典order
,它为后续的分组查询提供排序。另一个关键想法是使用group-by的resultSelector对元素进行排序(因为它们代表列)。
答案 1 :(得分:1)
在考虑了这个之后,这就是我想出来的。它或多或少与Kirk相同,但不使用字典。我的目标是一个单一的查询,(选择...进入)真的救了我。
var query = from item in data
where item.RowLabel == "All"
orderby item.Value descending
select item.ColumnLabel into columnOrder
join item in data on columnOrder equals item.ColumnLabel
group item by item.RowLabel;
var lquery = data.Where(item => item.RowLabel == "All")
.OrderByDescending(item => item.Value)
.Select(item => item.ColumnLabel)
.Join(data, columnOrder => columnOrder,
item => item.ColumnLabel,
(columnOrder, item) => item)
.GroupBy(item => item.RowLabel);