2016-10-19 2 views
0

У меня нет большого опыта работы с DataSets и вы не смогли найти лучший способ добиться того, чего я хочу достичь.Извлечение первого (самого старого) значения из набора данных на основе значения столбца

Я в основном создаю DataSet с использованием SQL Query, а затем я пытаюсь найти конкретное значение в столбце «Поле», а затем, если в «Флаге» есть «Y» (как указано в «N» ') Столбец в той же строке, затем я хочу, чтобы он изменил состояние флажка на «Проверено», а также обновил текст меток.

То, что я, кажется, работает, однако, если данные не возвращаются, я получаю ошибку ниже:

Object reference not set to an instance of an object

Если я немного изменить код из .FirstOrDefault() до .Первого() Я получаю эту ошибку:

Sequence contains no elements

Часть кода, который, как представляется, вызывает проблему, приведен ниже. Если вам нужно знать что-нибудь еще я добавлю его в

Dim sSQL As String 
    sSQL = 
     <SQL> 
      SELECT MAX(UpdateTime) AS UpdateTime FROM AdminCS_Data_Current 
      WHERE UpdateUser = |@@UpdateUser| 
     </SQL> 
    sSQL = Replace(sSQL, "@@UpdateUser", AdminCB.Text) 
    Me.LastUserUpdate.Text = "Last Action: " & Format(ReturnDatabaseValue(sSQL, "UpdateTime", "Data"), "dd/MM/yyyy HH:mm:ss") 

    Dim EmployeeDataset As New DataSet 
    Try 
     sSQL = 
      <SQL> 
       SELECT * FROM AdminCS_Data_Current 
       WHERE UpdateUser = |@@UpdateUser| AND CONVERT(DATE, UpdateTime) = CAST(GETDATE() AS DATE) 
       ORDER BY UpdateTime ASC 
      </SQL> 
     sSQL = Replace(sSQL, "@@UpdateUser", AdminCB.Text) 
     EmployeeDataset = ReturnDataSet(sSQL, "Data") 

     If EmployeeDataset IsNot Nothing Then 
      Dim eData = EmployeeDataset.Tables(0) 
      If (eData.Select("Field = 'Timesheets Checked'").FirstOrDefault()("Flag")) IsNot Nothing Then 
       If eData.Select("Field = 'Timesheets Checked'").FirstOrDefault()("Flag").ToString.Trim = "Y" Then 
        TShtY.CheckState = CheckState.Checked 
        TShtTime.Text = Format(eData.Select("Field = 'Timesheets Checked'").First()("UpdateTime"), "HH:mm:ss") 
       Else 
        TShtN.CheckState = CheckState.Checked 
       End If 
      End If 
      ' The above two IF statements would be repeated several times on each change of "Field" 
     End If 
+0

Весь смысл использования 'FirstOrDefault' заключается в том, что в последовательности не может быть ничего, поэтому вы не можете просто использовать результат, как если бы он есть. После вызова 'FirstOrDefault' вы должны проверить результат, чтобы увидеть, является ли это' Nothing' первым, а затем использовать его, если это не так, то есть использовать результат только в том случае, если это что-то. – jmcilhinney

+0

Если это недостаточно ясно, подумайте об этом. Предположим, что вы входите в комнату, в которой есть ноль, один или несколько человек, и я говорю вам, что вы можете собрать 100 долларов от первого человека, которого вы встречаете в этой комнате. Если вы войдете, и нет людей, то в вашем кармане материализуется $ 100? Конечно, нет, вы можете собирать только деньги, если есть человек, чтобы его собрать. Аналогично, вы можете использовать только первый элемент в последовательности, если в этой последовательности есть хотя бы один элемент. 'First' требует хотя бы одного элемента, а' FirstOrDefault' возвращает 'Nothing', если нет элементов. – jmcilhinney

+0

@jmcilhinney Разве это не то, что я сделал? Если в последовательности нет ничего уверенного, что IF (IsNot Nothing) не будет введен, и он пойдет прямо в конец IF? –

ответ

2

Казалось бы, что этот код введен не только iunefficiency, но и ошибка:.

If (eData.Select("Field = 'Timesheets Checked'").FirstOrDefault()("Flag")) IsNot Nothing Then 
     If eData.Select("Field = 'Timesheets Checked'").FirstOrDefault()("Flag").ToString.Trim = "Y" Then 
      TShtY.CheckState = CheckState.Checked 
      TShtTime.Text = Format(eData.Select("Field = 'Timesheets Checked'").First()("UpdateTime"), "HH:mm:ss") 
     Else 
      TShtN.CheckState = CheckState.Checked 
     End If 
    End If 

Он должен быть написан как это в первую очередь:

Dim row = eData.Select("Field = 'Timesheets Checked'").FirstOrDefault() 

    If row IsNot Nothing Then 
     If row("Flag").ToString.Trim = "Y" Then 
      TShtY.CheckState = CheckState.Checked 
      TShtTime.Text = Format(row("UpdateTime"), "HH:mm:ss") 
     Else 
      TShtN.CheckState = CheckState.Checked 
     End If 
    End If 

Легче читать, более эффективно и избегать этой неприятной ошибки.

Кроме того, я бы предпочел увидеть это:

Dim row = eData.Select("Field = 'Timesheets Checked'").FirstOrDefault() 

    If row IsNot Nothing Then 
     If row("Flag").ToString.Trim = "Y" Then 
      TShtY.Checked = True 
      TShtTime.Text = CDate(row("UpdateTime").ToString("HH:mm:ss") 
     Else 
      TShtN.Checked = True 
     End If 
    End If 

Вы никогда не должны использовать CheckState в виде Checkbox, если это не три-состояние, которое может быть вашей, но я сомневаюсь в этом. Что касается Format, мы больше не в VB6 Toto.

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