2016-01-28 5 views
-1

У меня есть метод, который будет принимать данные из БД, и я хотел бы вернуть один объект назад.Попытка понять LINQ

Однако следующий код вернет значение null.

Я уже проверял, что вход dt содержит 1 запись.

Этот метод работает, если я изменяю тип возвращаемого объекта с объекта на список объектов.

Я связываюсь, чтобы понять, почему в этом случае и почему я не могу вернуть только один объект.

public PersonObj GetPersonInformation(string personName) 
    { 
     DataTable dt = _oracle.GetPersonInformation(personName); 
     var aPerson = dt.AsEnumerable().Select(x => 
        new PersonObj 
        { 
         FirstName = x.Field<string>("FIRST_NAME"), 
         LastName = x.Field<string>("LAST_NAME"), 
         PhoneNumber = x.Field<string>("PHONE_NUMBER") 
        }).ToList().Take(1); 

     return aPerson as PersonObj; 
    } 
+2

Из связанного дубликата: «Наконец, разница между First() и Take() заключается в том, что First() возвращает сам элемент, а Take() возвращает последовательность элементов, содержащую ровно один элемент. (Если вы передаете 1 как параметр). " –

+0

Сторона примечания: ожидается, что автор вопроса выполнит некоторое базовое исследование (т.е. прочитает статьи MSDN по каждому методу, используемому в вопросе для C#), не делая этого (или не демонстрируя результаты), не очень хорошо отражается на авторе, а также может (даже если сообщение ничего не случилось - они не могут исправить себя) –

ответ

1

Take(1) Вместо того, делают First() или FirstOrDefault()

Take(n) возвращает IEnumerable графа n (в вашем случае, IEnumerable графа 1), тогда как First() возвращает первый объект в IEnumerable.

+0

Это сработало, но почему я не могу использовать Take (1)? – PrivateJoker

+2

, потому что Take (1) не возвращает один объект, он возвращает список, содержащий один объект. (Кстати, я имею в виду список в общем смысле, а не список ) – Joe

+0

@JDS См. мое редактирование. 'Take()' - это общий метод, который будет возвращать 'IEnumerable', сколько бы вы его не дали. По этой причине он согласуется с возвратом 'IEnumerable' count 1 вместо первого элемента. –

1

Вы пытались использовать FirstOrDefault() вместо Take (1)? Это должно позволить вам указать, что вы ожидаете только одного результата. Я считаю, что причина, по которой у вас возникла проблема с типом данных, связана с вызовами ToList() и Take(), которые могут возвращать более одного объекта.

2

Ваша проблема в том, что Take возвращает IEnumerable. Это связано с тем, что вы можете указать сумму, которую нужно принять. Что произойдет, например, если вы это сделаете?

public PersonObj GetPersonInformation(string personName, int take) 
     { 
      DataTable dt = _oracle.GetPersonInformation(personName); 
      return dt.AsEnumerable().Select(x => 
         new PersonObj 
         { 
          FirstName = x.Field<string>("FIRST_NAME"), 
          LastName = x.Field<string>("LAST_NAME"), 
          PhoneNumber = x.Field<string>("PHONE_NUMBER") 
         }).ToList().Take(take); 

     } 

Вы можете попросить (и получить) один, но вы можете попросить больше. Это показывает, почему вы получаете ошибку: Take(1) возвращает IEnumerable с 1 элементом, а не с одним элементом.

Если вы просто хотите первый, вы можете позвонить по номеру First().

+0

Используйте FirstOrDefault(), а не First(), чтобы избежать возможных исключений. – Joe

+2

@ Это ваше мнение ... Нет причин не использовать 'First', если вы точно знаете, что есть элемент для возврата, или если вы предпочтете исключение получает. – DrewJordan

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