2015-03-30 2 views
4

У меня есть таблица ProjectInformation, как (левая таблица)LINQ влево присоединиться только строки, имеющей максимальное значение столбца

ProjectID int 
{fields} 

другой таблицы, ProjectUpdates (правая таблица). Эта таблица содержит несколько записей для 1 ProjectID, добавленных ежемесячно.

ProjectID int 
CreateDate date 
{other fields that have records} 

Их отношение 1-М. Примеры данных

ProjectInformation 
{ ProjectID = 1, DataA = "ABC"} 
{ ProjectID = 2, DataA = "DEF"} 
{ ProjectID = 3, DataA = "GHI"} 

ProjectUpdates 
{ProjectID = 1, CreateDate = "24/2/2014", DataB = "JKL"} 
{ProjectID = 1, CreateDate = "25/1/2014", DataB = "MNL"} 
{ProjectID = 1, CreateDate = "23/12/2014", DataB = "PQR"} 
{ProjectID = 1, CreateDate = "23/11/2014", DataB = "STU"} 
{ProjectID = 2, CreateDate = "24/2/2014", DataB = "VWX"} 
{ProjectID = 2, CreateDate = "24/1/2014", DataB = "YZA"} 
{ProjectID = 3, CreateDate = "21/12/2014", DataB = "BCD"} 
{ProjectID = 3, CreateDate = "24/11/2014", DataB = "EFG"} 
{ProjectID = 3, CreateDate = "24/10/2014", DataB = "HIJ"} 
{ProjectID = 3, CreateDate = "24/8/2014", DataB = "KLM"} 
{ProjectID = 3, CreateDate = "24/6/2014", DataB = "NOP"} 

Я хочу, чтобы мой запрос LINQ, чтобы вернуть следующие данные (1 строка для каждого проекта)

Критерии: Строка в таблице слева будет присоединиться к одному в праве, которая имеет самый большой значение CreateDate для проекта.

{ProjectID = 1, CreateDate = "24/2/2014", DataA ="ABC", DataB = "JKL"} 
{ProjectID = 2, CreateDate = "24/2/2014", DataA ="DEF", DataB = "VWX"} 
{ProjectID = 3, CreateDate = "21/12/2014", DataA ="GHI", DataB = "BCD"} 
+1

Возможно, вам захотелось показать идентификаторы различных проектов в результирующем наборе данных. Кстати, вы что-то пробовали? –

+0

FYI: В вашем примере вывода все имеет тот же 'ProjectID'' 1'. Это должно быть '1 2 & 3'. – Jamiec

+0

@Jamiec благодарит за это. Изменено –

ответ

2

Вы можете сделать это разными способами. Один из тех, кто, как это:

var result = (from pi in projectInformations 
       join pu in projectUpdates on pi.ProjectID equals pu.ProjectID into tpu 
       from t in tpu.OrderByDescending(c => c.CreateDate).Take(1) 
       select new { pi.ProjectID, pi.DataA, t.CreateDate, t.DataB }).ToList(); 
+0

Я просто подошел к очень близкому решению, так или иначе, вот тестовый код, который я использовал http://rextester.com/KLPBI85561 – Jamiec

2

Вы можете использовать one to many ассоциацию от ProjectInformation к ProjectUpdate и OrderByDescending/FirstOrDefault.

public class ProjectInformation { 
    public int ProjectID { get; set; } 
    public virtual ICollection<ProjectUpdate> ProjectUpdates { get; set; } 
} 

db.Project 
    .Select(p => new { 
    ProjectID = p.ProjectID, 
    MostRecentProjectUpdate = p.ProjectUpdates.OrderByDescending(u => u.CreateDate).FirstOrDefault() 
}); 

Примечание: Использование OrderByDescending может быть сложно, если CreateDate является строка, а не дата в вашей базе данных.

+0

Объект или сложный тип '' не могут быть сконструированы в запросе LINQ to Entities. Моя Запрос вар проекты = от р в _context.PROJECTINFORMATION где p.ISACTIVE == "Y" выбрать новый PROJECTINFORMATION() { ProjectID = p.PROJECTID, PROJECTSUMMARYUPDATES = (ICollection ) p.PROJECTSUMMARYUPDATES .OrderByDescending (x => x.UPDATEFORMONTH) .FirstOrDefault() }; return projects.ToList(); –

0

Попробуйте это: -

var result = (from pi in projectInfo 
       join pu in projectupdates 
       on pi.ProjectID equals pu.ProjectID into g 
       let data = g.OrderByDescending(x => DateTime.ParseExact(x.CreateDate, 
          "dd/M/yyyy", CultureInfo.InvariantCulture)).FirstOrDefault() 
       select new 
       { 
        ProjectID = data.ProjectID, 
        CreatedDate = data.CreateDate, 
        DataA = pi.DataA, 
        DataB = data.DataB 
       }).ToList(); 

Working Fiddle.

Обратите внимание: поскольку я использую FirstOrDefault, вам необходимо проверить, не являются ли данные недействительными до доступа к его свойствам.

Смежные вопросы