none
Index out of range exception

    Question

  • I am looping in my datatable searching for certain values and whenever I find them I remove them from thet datatable. I am using the code below to do this
         If myTable.Rows.Count = 0 Then
    
                Else
                    'Try
                    For Each myDataRow As DataRow In dTable.Rows
                        For myArraySearch As Integer = 0 To 50 Step 1
                            dTable.Rows.RemoveAt(dTable.Rows.IndexOf(dTable.Rows.Find(myArray(myArraySearch))))
                        Next
                    Next
                    'Catch ex As Exception
                    'End Try
                End If
    When I remove the try catch statement I get the error that says "There is no row at position -1.".Is there a better way to contain this rather than the try catch.

    If you think it you can achieve it

    Friday, July 27, 2012 11:02 AM

Answers

  • Removing the exception handler was a good first step. 

    Obviously, the IndexOf function does not find what you pass, hence it returns -1. This is because the Find function called before returned Nothing because it didn't find what you've passed in. To find out why, whenever the exception occurs, examine the value in myArray(myArraSearch) and verify if it makes sense that the row is not found. You may also consider splitting the line into two:

                   Dim row = dTable.Rows.Find(myArray(myArraySearch))
                   dTable.Rows.RemoveAt(dTable.Rows.IndexOf(row))
    

    Now you can easier have a look at the 'row' content when debugging.

    In addition, the outer loop does not make sense at all. You do not even use variable 'myDataRow'.

    Moreover, you are complication the task: You do not have to look for the index first, then call RemoveAt. Instead, just call Remove:

    dTable.Rows.Remove(row)

    Be aware it really removes the row. If you plan to synchronize the datatable with a database later, no delete will be performed. Then you should call row.Delete instead.

    Is it intended that you use 'myTable' at the beginning and 'dTable' later?


    Armin

    • Marked as answer by tendaimare Friday, July 27, 2012 12:41 PM
    Friday, July 27, 2012 11:18 AM
  • Thanks so much guyz I am now using the code below. I am still thinking whether to put rows.delete or the other way but thanks so much
        For Each key In myArray
                        Dim row = dTable.Rows.Find(key)
    
                        If row IsNot Nothing Then
                            dTable.Rows.Remove(row)
                            'row.Delete()
                        End If
                    Next

    :

    If you think it you can achieve it

    • Marked as answer by tendaimare Friday, July 27, 2012 12:42 PM
    Friday, July 27, 2012 12:41 PM

All replies

  • Start by removing the outer loop ( For each ... ) and check if the error is gone.

    You don`t do anything with this loop.


    Hannes

    If you have got questions about this, just ask.

    In a perfect world,
    users would never enter data in the wrong form,
    files they choose to open would always exist
    and code would never have bugs.

    C# to VB.NET: http://www.developerfusion.com/tools/convert/csharp-to-vb/

    Friday, July 27, 2012 11:08 AM
  • Removing the exception handler was a good first step. 

    Obviously, the IndexOf function does not find what you pass, hence it returns -1. This is because the Find function called before returned Nothing because it didn't find what you've passed in. To find out why, whenever the exception occurs, examine the value in myArray(myArraSearch) and verify if it makes sense that the row is not found. You may also consider splitting the line into two:

                   Dim row = dTable.Rows.Find(myArray(myArraySearch))
                   dTable.Rows.RemoveAt(dTable.Rows.IndexOf(row))
    

    Now you can easier have a look at the 'row' content when debugging.

    In addition, the outer loop does not make sense at all. You do not even use variable 'myDataRow'.

    Moreover, you are complication the task: You do not have to look for the index first, then call RemoveAt. Instead, just call Remove:

    dTable.Rows.Remove(row)

    Be aware it really removes the row. If you plan to synchronize the datatable with a database later, no delete will be performed. Then you should call row.Delete instead.

    Is it intended that you use 'myTable' at the beginning and 'dTable' later?


    Armin

    • Marked as answer by tendaimare Friday, July 27, 2012 12:41 PM
    Friday, July 27, 2012 11:18 AM
  • FYI, you should never remove rows from a DataTable using a For Each...Next clause. When you remove a row the DataTable is re-indexed, so it's best to start with the last item in the DataTable first and then proceed in the reverse direction until you have reached the first row. Use a For...Next with a Step - 1 instead.

    Paul ~~~~ Microsoft MVP (Visual Basic)

    Friday, July 27, 2012 11:58 AM
  •  Okay , Now it says "Object reference not set to an instance of an object"

                    For myArraySearch As Integer = 0 To 50 Step 1
                        'dTable.Rows.RemoveAt(dTable.Rows.IndexOf(dTable.Rows.Find(myArray(myArraySearch))))
                        Dim row = dTable.Rows.Find(myArray(myArraySearch))
                        row.Delete()
                        'dTable.Rows.RemoveAt(dTable.Rows.IndexOf(row))
                    Next

    and its pointing at row.delete.


    If you think it you can achieve it

    Friday, July 27, 2012 12:17 PM
  • Thanks so much guyz I am now using the code below. I am still thinking whether to put rows.delete or the other way but thanks so much
        For Each key In myArray
                        Dim row = dTable.Rows.Find(key)
    
                        If row IsNot Nothing Then
                            dTable.Rows.Remove(row)
                            'row.Delete()
                        End If
                    Next

    :

    If you think it you can achieve it

    • Marked as answer by tendaimare Friday, July 27, 2012 12:42 PM
    Friday, July 27, 2012 12:41 PM