2

I am trying to delete every row in which the value "X" is found in column B using VBA. However, I'm having three problems:

  1. I can't get my VBA code to move down from the active cell to the next cell (B3) using cells.find method (see code below)
  2. My code does not delete the entire row where the value "X" is found in column B
  3. The amount of Data in Column B can vary: it can end at B10 today, or B100 tomorrow (see screen shot below)

Any assistance will be greatly appreciated.

Sub RemoveRows()   
    Dim strLookFor As String
    Dim strRow As String

    Worksheets("Sheet1").Range("B2").Activate

    strLookFor = "X"
    strRow = Range("B2").Address

    Do Until ActiveCell.Value = ""        
        MsgBox (ActiveCell.Value)        
        If ActiveCell.Value = strLookFor Then
            Rows.Delete (strRow)
        End If            
        strRow = Cells.Find(what:=strLookFor).Address
    Loop

    MsgBox ("Deleted all rows with value " & strLookFor)    
End Sub

enter image description here

Community
  • 1
  • 1
Anthony
  • 3,990
  • 23
  • 68
  • 94

3 Answers3

6

Using an AutoFilter is much more efficient than a range loop

Sub QuickCull()
Dim ws As Worksheet
Dim rng1 As Range
Set ws = Sheets("Sheet1")
Set rng1 = ws.Range(ws.[b2], ws.Cells(Rows.Count, "B").End(xlUp))
Application.ScreenUpdating = False
With ActiveSheet
        .AutoFilterMode = False
        rng1.AutoFilter Field:=1, Criteria1:="X"
        rng1.Offset(1, 0).EntireRow.Delete
        .AutoFilterMode = False
    End With
Application.ScreenUpdating = True
End Sub
brettdj
  • 54,857
  • 16
  • 114
  • 177
  • AutoFilter is very interesting. I'm studying it now. Thanks a lot! – Anthony Nov 29 '12 at 19:41
  • I'm really new into this subject; could you please explain me what does these two line do? 1- `Set rng1 = ws.Range(ws.[b2], ws.Cells(Rows.Count, "B").End(xlUp))` and 2- `rng1.Offset(1, 0).EntireRow.Delete`. – Zeinab Abbasimazar Aug 12 '14 at 12:57
  • 4
    @Zeinab Abbasi : even though it is late, it may well help others: `Set rng1 = ws.Range(ws.[b2], ws.Cells(Rows.Count, "B").End(xlUp)) ` Is specifying the Range from B2 to the last Row in B... `Rows.Count, "B").End(xlUp) ` counts the Rows in Column B. Since there might be empty rows in between, it is adviced to start counting bottom up to get the last used row. The Offset says: spare the header Row(1) but other than that delete the Entire row, that matches the criteria. (By hand you'd click a filter, limit the visible ones to that filter and select the rest, then hit DEL ) Hope that helped. – AnyOneElse Mar 09 '15 at 15:06
  • @AnyOneElse good clarification - I'd missed the initial follow-up query – brettdj Mar 09 '15 at 21:49
  • @AnyOneElse, it is absolutely too late :D; but thanks for your response. It's really nice of you! :) – Zeinab Abbasimazar Mar 10 '15 at 10:32
2
dim x as long
dim r as long
dim sht as worksheet

set sht = Worksheets("Sheet1")
r = sht.Cells(rows.count,2).end(xlup).row 

for x = r to 2 step -1
    with sht.cells(x,2)
        if .value = "X" then .entirerow.delete
    end with 
next x
Tim Williams
  • 154,628
  • 8
  • 97
  • 125
1

This should work:

Sub DeleteRowsWithX()

maxRow = ActiveSheet.UsedRange.Rows.Count

For i = 1 To maxRow
    Do While (StrComp(ActiveSheet.Cells(i, 2).Text, "X", vbTextCompare) = 0)
        Rows(i).Select
        Selection.Delete Shift:=xlUp
   Loop
Next

End Sub
David
  • 6,462
  • 2
  • 25
  • 22