クエリ式わかんない

 外部から与えられたデータを使いやすいようにオブジェクトの構造を組み変えるため、こんなコードを書いた。

static zHinMoku[] Compose(zYearItem[] items, string suffix)
{
	var flats = 
		from yearItem in items
		from data in yearItem.Data
		from ps in data.Data
		select new
		{
			Name = data.Name + suffix,
			yearItem.Year,
			ps.Location,
			ps.Season,
			ps.Data
		};

	return flats
		.GroupBy(flat => flat.Name)
		.Select(g => new zHinMoku(g.Key, new zDataList(g
			.GroupBy(flat => flat.Location)
			.SelectMany(g2 => g2
				.GroupBy(flat => flat.Season)
				.Select(g3 => new zDataTop(g2.Key, g3.Key, new zYearList(g3
					.Select(flat =>{
						var d = flat.Data;
						return new zYear(flat.Year, d.Data1, d.Data2, d.Data2_10a, d.Data3, d.Data3_10a);
					}).ToArray()
				)))
			).ToArray()
		))).ToArray();
}

 一旦木をばらして表にして、GroupByを連打して新しい木に組み替えようとしている。

 この下の方のGroupBy連打をクエリ式で書く方法が分からない。group by intoの後にそれまでの文脈の情報を伝える方法が分からない。

 LocationとSeasonで別々にグループを作っているが、匿名型を使うと二つの値をKeyに出来る。EqualsとGetHashCodeが自動でオーバーライドされる。

 二つの値を使ってKeyにすればここで必要な情報は取れる。

return
	(from flat in flats
	group flat by flat.Name into nameGroup
	select new zHinMoku(nameGroup.Key, new zDataList(
		(from nameItem in nameGroup
		 group nameItem by new { nameItem.Location, nameItem.Season } into seasonGroup
		 select new zDataTop(seasonGroup.Key.Location, seasonGroup.Key.Season, new zYearList(
			 (from seasonItem in seasonGroup
			  let d = seasonItem.Data
			  select new zYear(seasonItem.Year, d.Data1, d.Data2, d.Data2_10a, d.Data3, d.Data3_10a)
			 ).ToArray()
		 ))).ToArray()
	 ))).ToArray();

 でもなんか怪しいんだよなあ。クエリ式は嫌いだ。JoinもGroupByも俺にはメソッド形式の方が書きやすい。