1

FluentNHibernate を介してマッピングされた次のドメインがあります

class Point
{
    public int Id { get; set; }
    public string Label { get; set; }
}

class PointData
{
    public int Id { get; set; }        
    public DateTime Hour { get; set; } 
    public decimal Value { get; set; }
    public Point Location { get; set; }
    public DateTime Available { get; set; } // Data arrival (data tracking)
}

PointData テーブルは、Hour の新しい値を挿入して頻繁に更新されますが (更新はサポートされていません)、すべてのポイントが同じ頻度で PointData を書き込むわけではありません。

startTime と endTime の間、および timeOfSnapshot(available) より前のすべての時間について、Point ごとに最新の PointData を取得する必要があります。

これまでのところ、Linq を使用して group by を使用して Nhibernate を使用したクエリは機能しません。

Query.Where(x => x.Available <= available && x.Hour >= startHour && x.Hour < endHour)
                    .OrderByDescending(x => x.Available)
                    .GroupBy(x => new {x.Location, x.Hour})
                    .Select(g => g.First())
                    .ToList();

これまでのすべての検索では SQL クエリしか出てきませんでしたが、これはまさに私が望んでいるものではありません。

助けが必要です

4

2 に答える 2

1

group by 結果を元の行と結合し、行を返します。

rows.Join(
   rows.GroupBy(x => new {x.Location, x.Hour}), 
   x => new {x.Location, x.Hour, x.Available}, 
   g => new {g.Key.Location, g.Key.Hour, Available = g.Max(p=>p.Available)},
   (x1,g1) => x1
)

プロファイラーをオンにすると、次の sql が表示されます。

SELECT [t0].*
FROM [rows] AS [t0]
INNER JOIN (
    SELECT MAX([t1].[Available]) AS [value], [t1].[Location], [t1].[Hour]
    FROM [rows] AS [t1]
    GROUP BY [t1].[Location], [t1].[Hour]) 
AS [t2] ON (
    [t0].[Location] = [t2].[Location]) 
    AND ([t0].[Hour] = [t2].[Hour]) 
    AND ([t0].[Available] = [t2].[value]
)
于 2013-02-08T07:26:16.683 に答える
0

group byの後で、グループ化キーまたは集計で使用されているよりも多くの列を抽出することはできません。私があなたの質問を正しく理解している場合、これの通常のパターンは、関心のある行の識別子を選択するサブクエリを使用し、次にそれらの行のすべての列を取得するための外部クエリを使用することです。次のようなものを試してください。

var latestPointId =
    Query.Where(x => x.Available <= available && x.Hour >= startHour && x.Hour < endHour)
        .OrderByDescending(x => x.Available)
        .GroupBy(x => new {x.Location, x.Hour})
        .Select(g => g.Max(pd => pd.Id));

session.Query<PointData>
    .Where(pd => latestPointId.Contains(pd.Id)
    .ToList();
于 2013-02-06T07:45:01.257 に答える