LINQ-to-entities жалпы == уақытша жою

Менде келесі LINQ-субъектілер сұрауы бар

IQueryable> GetFirstOperationsForEveryId
    (IQueryable> ItemHistory)
{
    var q = (from h in ItemHistory
             where h.OperationId ==
                (from h1 in ItemHistory
                 where h1.GenericId == h.GenericId
                 select h1.OperationId).Min()
             select h);
    return q;
}

ItemHistory is a generic query. It can be obtained in the following way

var history1 = MyEntitiySet1.Select(obj =>
    new History{ obj.OperationId, GenericId = obj.LongId });
var history2 = AnotherEntitiySet.Select(obj =>
    new History{ obj.OperationId, GenericId = obj.StringId });

In the end of all I want a generic query being able to work with any entity collection convertible to History.

Мәселе ішкі сұраныста GenericId салыстыруынан (Оператор '==' 'T' және 'T' түріндегі операндаларға қолданылмайды) байланысты компиляция емес кодын жасамайды.

Мен h1.GenericId.Equals (h.GenericId) параметрін == өзгертсем, келесі NotSupportedException аламын:

'System.Int64' түрін 'System.Object' деп теру мүмкін емес. LINQ to Entities тек Entity Data Model қарабайыр түрлері түрлерін қолдайды.

Ішкі сұраныстың орнына топтастыруды және нәтижелерге қосылуға тырыстым.

IQueryable> GetFirstOperationsForEveryId
    (IQueryable> ItemHistory)
{
    var grouped = (from h1 in ItemHistory
                   group h1 by h1.GenericId into tt
                   select new
                   {
                        GenericId = tt.Key,
                        OperationId = tt.Min(ttt => ttt.OperationId)
                   });

    var q = (from h in ItemHistory
             join g in grouped
                on new { h.OperationId, h.GenericId }
                equals new { g.OperationId, g.GenericId }
             select h);
    return q;
}

GenericId-ді equals кілт сөзімен салыстырғандықтан, ол жасалады, бірақ нақты деректермен сұрау тым баяу (ол арнайы postgresql серверінде 11 сағат бойы жұмыс істейді).

Сыртқы мекенжайға арналған өрнектің толық нұсқасын жасау мүмкіндігі бар. Бірақ код өте ұзақ және түсініксіз еді.

LINQ-субъектілерінде генериктермен теңдік салыстыру үшін қарапайым шешімдер бар ма?

2
қосылды редакцияланған
Көріністер: 5

4 жауаптар

Бұл әрекетті байқап көріңіз, менің ойымша, қосымша сұраныс/қосылусыз қалаған нәрсені орындау керек

IQueryable> GetFirstOperationsForEveryId
    (IQueryable> ItemHistory)
{
  var q = from h in ItemHistory
          group h by h.GenericId into tt
          let first = (from t in tt
                        orderby t.GenericId
                        select t).FirstOrDefault()
          select first;

  return q;
}
1
қосылды
Әсіресе талғампаз шешім! Бірақ, өкінішке орай, Npgsql-де (2.0.11.92 жағдайында) іске асырылмады. System.Data.EntityCommandCompilationException: Пәрмен анықтамасын дайындау кезінде қате пайда болды. ---> System.NotImplementedException: әдіс немесе операция орындалмады. Менің нақты мәселе индекстерді жасауды ұмытып кеткен болатын. Нақ сондықтан топ + қосылуға сұрау 11 сағат жұмыс істеді. Индекстермен ол өте жылдам жұмыс істейді.
қосылды автор Mike, көзі

Сондай-ақ, GenericId және OperationId сипатын іске асыратын IItemHistory inteface үшін T арналған жалпы шектеулерді орнатуға болады.

0
қосылды

Менің сұрағымда шешім бар. + Group + қосылымымен екінші әдіс кесте дұрыс индекстелген болса жақсы жұмыс істейді. Дерекқор кестесінен 370к жолдарды алу үшін 3,28 секунд қажет. Шындығында жалпы емес нұсқада бірінші сұраныс postgresql-дегі екіншіге қарағанда баяуырақ болады. 26,68 секундқа қарсы 4.75.

0
қосылды
IQueryable> GetFirstOperationsForEveryId
(IQueryable> ItemHistory)
{
var grouped = (from h1 in ItemHistory
               group t by h1.GenericId into tt
               select new
               {
                    GenericId = tt.Key,
                    OperationId = tt.Min(ttt => ttt.OperationId)
               });

var q = (from h in ItemHistory
         join g in grouped
            on new { h.OperationId, h.GenericId }
            equals new { g.OperationId, g.GenericId }
         select h);
return q;
}
0
қосылды
Мен жіберген нәрселерден қандай айырмашылық бар?
қосылды автор Mike, көзі