简体   繁体   中英

If with multiple or statements creating endless loop

I have a loop that goes down a column and identifies if the cell equals to one of the listed security types. If it does not, it will cut and paste the data offset 1 column to the left. Sometimes the data is offset 1-3 columns which is why i added the i = i - 1 to check the same row until it satifies the if. This code leads to 2 issues:

1.) Is there a more simple line of code for the If statement with multiple or's?

2.) This code works in sections but when it runs on the whole sheet (~29K rows) it enters into an endless loop. Any ideas why this happens?

LastCashrow = Sheets("Cash Data").Range("A" & Sheets("Cash Data").Rows.Count).End(xlUp).Row

For i = 8 To LastCashrow

SecType = Left(Cells(i, 5), 2)

  If SecType = "aw" Or SecType = "ca" Or SecType = "cb" Or SecType = "cd" Or SecType = "cl" Or SecType = "cp" Or SecType = "cs" Or SecType = "cv" Or SecType = "ep" _
                Or SecType = "ex" Or SecType = "fi" Or SecType = "fm" Or SecType = "gb" Or SecType = "gm" Or SecType = "hf" Or SecType = "lp" Or SecType = "mb" _
                Or SecType = "mf" Or SecType = "oa" Or SecType = "pf" Or SecType = "pr" Or SecType = "ps" Or SecType = "pt" Or SecType = "re" Or SecType = "rl" _
                Or SecType = "tb" Or SecType = "tp" Or SecType = "ut" Or SecType = "wt" Or SecType = "zb" Or SecType = "zt" Then

  ElseIf IsEmpty(SecType) = "True" Then
        Exit For

  Else
        Set Shift = Range(Cells(i, 5), Cells(i, 17))
        Shift.Cut
        Cells(i, 4).Select
        ActiveSheet.Paste
        Application.CutCopyMode = False
        i = i - 1

  End If

Next i

1.) Is there a more simple line of code for the If statement with multiple or's?

Yes. I'd start by improving your code this way:

' Declare all of your variables explicitly
Dim LastCashRow As Long
Dim i As Long
Dim SecType As String
Dim cell As Range

Dim validSecTypes() As String
validSecTypes = Split("aw,ca,cb,cd", ",") ' write all of your values here...
' returns an array of strings: ["aw", "ca", "cb", "cd"]

LastCashRow = 12

For i = 8 To LastCashRow
    Set cell = Cells(i, 5)
    If IsEmpty(cell) Then Exit For ' This is really the first thing to check for.

    SecType = Left(cell.Value, 2)

    If ArrayContains(validSecTypes, SecType) Then 
        MsgBox SecType & " is IN!"
    Else
        MsgBox "This is OUT: " & SecType
        'your lines of code go here
    End If

Next i

This uses the helper function:

Function ArrayContainsValue(arr As Variant, val As Variant) As Boolean
    ArrayContainsValue = (UBound(Filter(arr, val)) > -1)
End Function

2.) This code works in sections but when it runs on the whole sheet (~29K rows) it enters into an endless loop. Any ideas why this happens?

No. We'd have to see your sheet.

\n

But are you really sure it's endless? Because processing that many rows using your code as it currently is written can take some time.

As I had guessed, your code is just taking a long time to run.

The culprit is likely this bit of code:

    Shift.Cut
    Cells(i, 4).Select
    ActiveSheet.Paste

You could do this to simplify the multiple or condition:

If InStr(1, "/aw/ca/cb/cd/cl/cp/cs/cv/ep/ex/fi/fm/gb/gm/hf/lp/mb/mf/oa" + _
            "/pf/pr/ps/pt/re/rl/tb/tp/ut/wt/zb/zt", SecType) > 1 Then

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM