Структура сущностей с двумя объединениями в одной таблице для столбца 1 или столбца 2 - PullRequest
0 голосов
/ 08 февраля 2019

Я пытаюсь создать запрос EF для возврата столбца 1 или столбца 2.

Столбец 1 извлекается из другой таблицы на основе отношений / соединения запроса.

Столбец 2 извлекается из объединенной таблицы.

Это модель опроса / ответа.Некоторые ответы жестко закодированы (например, пользователь выбирает из списка), а некоторые являются свободным текстом.

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

Конечная цель - создать класс POCO с вопросом и ответом:

public class SurveyResponse
{
    public string Question { get; set; }
    public string Answer { get; set; }
}

Мой запрос выглядит следующим образом:

var surveyResponses = (from ias in dataContext.AnswerSet
                       join answer in dataContext.Answer on ias.AnswerSetID equals answer.AnswerSetID
                       join oa in dataContext.OptionalAnswer on answer.PossibleAnswerID equals oa.OptionalAnswerID // this line loses valuetext answer
                       where ias.LeadID.Equals(dbLead.leadID)
                       select new SurveyResponse() { Question = "question(todo)", Answer = (answer.ValueText != "" ? answer.ValueText : oa.Title)}).ToList();

А вот некоторые данные, которые показывают, почему соединение наoptionanswer теряет последний ряд

PossibleAnswerID    ValueText
979D3ADF-4F9C-4F4D-AC9C-034CE960003A    
EF488701-683D-4855-A9A7-7F9D78468E63    
D442F616-6D4B-4176-9F08-133E2C655BE4    
5FD57A95-B385-4CAE-ADAB-1711CEA00A08    
NULL    Questions about sales

Ответы [ 2 ]

0 голосов
/ 09 февраля 2019

Очевидно, ваш запрос генерирует inner join в sql и, таким образом, исключает Answer с пустым PossibleAnswerID.Так что вам просто нужно изменить его на left join.Это можно сделать вот так

var surveyResponses = 
    (from ias in dataContext.AnswerSet
     join answer in dataContext.Answer on ias.AnswerSetID equals answer.AnswerSetID
     join oa in dataContext.OptionalAnswer on answer.PossibleAnswerID equals oa.OptionalAnswerID into optans // this line loses valuetext answer
     from oa in optans.DefaultIfEmpty()
     where ias.LeadID.Equals(dbLead.leadID)
     select new SurveyResponse() { Question = "question(todo)", Answer = (answer.ValueText != "" ? answer.ValueText : oa.Title)}).ToList();
0 голосов
/ 08 февраля 2019

Если вы используете свободный синтаксис, .Select может принять аргумент Expression<Func<TEntity, TResult>>.

Упрощенно:

Expression<Func<AnswerSetType, SomeClass>> func = SomeMethod();

dataContext.AnswerSet
    .Select(func)
    .ToList();

SomeClass может быть просто так в зависимости от того, что именно вам нужно:

public class SomeClass 
{
    public string ValueFromColumn1OrColumn2 { get; set; }
}

SomeMethod - это место, где вы должны определить, какойзначение должно быть возвращено из вашего запроса:

public Expression<Func<AnswerSetType, SomeClass>> SomeMethod()
{
    if (condition)
    {
        return (answerSetType => new SomeClass { ValueFromColumn1OrColumn2 = answerSetType.Column1 });
    }
    else
    {
        return (answerSetType => new SomeClass { ValueFromColumn1OrColumn2 = answerSetType.Column2 });
    }
}

В Expression вы также можете использовать свойства навигации для доступа к столбцам в другой таблице.

Я делаю предположениездесь оба ваших столбца имеют одинаковый тип данных.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...