Почему компилятор считает, что это объект вместо DataRow? - PullRequest
4 голосов
/ 02 августа 2010

Я использую запрос LINQ для перевода данных внутри объекта DataTable в простой IEnumerable пользовательского объекта POCO.

Мой запрос LINQ:

    Dim dtMessages As DataTable

    '...dtMessages is instantiated ByRef in a helper data access routine... '

    Dim qry = From dr As DataRow In dtMessages.Rows
              Select New OutboxMsg With {
                  .ComputerID = dr(dcComputerID),
                  .MessageData = dr(dcMessageData),
                  .OutBoxID = dr(dcOutBoxID),
                  .OutBoxReceivedID = dr(dcOutBoxReceivedID),
                  .TrxDate = dr(dcTrxDate)
              }

Однако компилятор выдает предупреждение под dr As DataRow с сообщением:

Option Strict On запрещает неявные преобразования из 'Object' в 'System.Data.DataRow'.

Почему я получаю эту ошибку и что мне нужно сделать, чтобы ее исправить?Я бы подумал, что dtMessages.Rows вернул коллекцию типа DataRow.Разве это не правильно?

Ответы [ 3 ]

12 голосов
/ 02 августа 2010

Lok на DataTable.Rows - это DataRowCollection, который реализует только IEnumerable, а не IEnumerable(Of DataRow).

К счастью, в DataTableExtensions есть метод расширения, который позволяет вам вызывать AsEnumerable() вместо Rows; AsEnumerable возвращает IEnumerable(Of DataRow):

Dim qry = From dr As DataRow In dtMessages.AsEnumerable()
          ...

(Я предпочитаю это, чем использовать dt.Rows.Cast(Of DataRow), так как это дает меньше впечатления о том, что может потерпеть неудачу. Это более приспособлено к DataTable. Хотя оба будут работать.)

8 голосов
/ 02 августа 2010

Тип System.DataTable предшествует обобщению в .Net и, следовательно, возвращает простой старый IEnumerable вместо IEnumerable(Of DataRow), хотя под капотом это экземпляры DataRow. Следовательно, тип dr в приведенном выше запросе - Object, а не DataRow.

Вы можете обойти это, используя метод расширения Cast, чтобы сделать тип коллекции явным

From dr As DataRow in dtMessages.Rows.Cast(Of DataRow)
3 голосов
/ 02 августа 2010

Свойство DataTable.Rows возвращает коллекцию DataRow, однако эта коллекция не реализует IEnumerable<DataRow>, но IEnumerable, которая работает как IEnumerable<Object>.

Вы можете явно привести элементы коллекции к DataRow, используя dtMessages.Rows.Cast<DataRow>().

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