Pertanyaan EF / Linq - Urutkan koleksi sebelum dikelompokkan


Saya memiliki hubungan satu-ke-banyak antara tabel proyek dan meja audit. Saya mencoba untuk memilih dari tabel audit entri terbaru untuk setiap entitas proyek.

Dari apa yang saya pahami untuk melakukan ini, saya harus dapat mengurutkan koleksi audit saya berdasarkan tanggal sebelum mengelompokkan berdasarkan id proyek, sehingga saya dapat memilih entri pertama untuk setiap grup (id proyek) untuk mendapatkan entri terbaru.

Tetapi ketika saya menjalankan kueri ef / linq, hasilnya tidak benar dan order-by tampaknya diabaikan - bahkan sql yang dihasilkan tidak termasuk perintah dengan pernyataan.

Inilah contoh sederhana yang saya coba.

using (var ctx = new MyDbContext())
{
    var audit = from a in ctx.ProjectAudits
                orderby a.CreatedDate descending
                group a by a.ProjectId into grp
                select grp.FirstOrDefault();

    var resultsList = audit.ToList();
}

Hasilnya selalu kembali dengan entri audit paling awal untuk setiap id proyek dan bukan yang terbaru.

Apakah ada yang salah dengan pertanyaan ini? apakah saya kehilangan sesuatu yang jelas?


4
2018-04-26 11:12


asal


Jawaban:


MEMPERBARUI

Oke, bagaimana dengan ini?

ctx.ProjectAudits
    .GroupBy(p => p.ProjectId)
    .Select(p => p.OrderByDescending(j => j.CreatedDate).FirstOrDefault())
    .ToList();

Tidak memiliki VS dengan saya di sini, tetapi secara teoritis harus mengelompokkan catatan Anda, memesannya di dalam grup berdasarkan tanggal pembuatannya, dan pilih rekaman pertama dari setiap grup.


4
2018-04-26 11:34



saya berpikir Anda perlu melihat pendekatan yang berbeda. Daripada memesan, kenapa tidak Anda kelompokkan dan kemudian pilih audit dengan maksimal CreatedDate. Saya belum menguji yang berikut ini dan saya hanya membuangnya di sana:

var audit = from a in ctx.ProjectAudits
            group a by a.ProjectId into grp
            select new {
              // whatever your other properties are
              CreatedDate = grp.Max(i => i.CreatedDate)
            };

Atau, karena kebanyakan orang lebih memilih sintaks metode:

var audit = ctx.ProjectAudits
               .Where(i => i.CreatedDate == ctx.ProjectAudits
                                               .Max(x => x.CreatedDate));

EDIT - membuat beberapa perubahan, dan diuji dengan kelas tes dan List<TestClass> dan di atas bekerja dengan itu.


1
2018-04-26 11:25