是否有一种方法可以在Excel VBA中同时对多个列运行自动筛选?

是否有一种方法可以在Excel VBA中同时对多个列运行自动筛选?,excel,vba,field,autofilter,Excel,Vba,Field,Autofilter,我有一个被指定为用户输入“UserSearch”搜索框的单元格,需要能够使用此输入同时过滤多个列。例如,如果用户搜索“Apple”,我需要VBA代码过滤掉该单词出现的所有行,即使它出现在另一列中。目前,我只能一次过滤掉一列,但该输入也可能出现在另一列中,但该行不会被过滤,因为它可能已被之前的列过滤掉 我目前的代码如下: Sub search() With ActiveSheet.Range("$a$4:$j$30") .AutoFilter Field:=1, Criter

我有一个被指定为用户输入“UserSearch”搜索框的单元格,需要能够使用此输入同时过滤多个列。例如,如果用户搜索“Apple”,我需要VBA代码过滤掉该单词出现的所有行,即使它出现在另一列中。目前,我只能一次过滤掉一列,但该输入也可能出现在另一列中,但该行不会被过滤,因为它可能已被之前的列过滤掉

我目前的代码如下:

Sub search()
    With ActiveSheet.Range("$a$4:$j$30")
       .AutoFilter Field:=1, Criteria1:="=*" & Range("UserSearch") & "*", Operator:=xlOr
       .AutoFilter Field:=2, Criteria1:="=*" & Range("UserSearch") & "*", Operator:=xlOr
       .AutoFilter Field:=3, Criteria1:="=*" & Range("UserSearch") & "*"
    End With
End Sub
如您所见,我的目标是能够在所有3个字段上同时运行autofilter,基本上将3列视为一列,但上面的代码相互矛盾,并且不返回任何行。任何人对使用autofilter有任何想法吗?

您不能使用autofilter,但可以使用一个小的vba代码实现您想要的

假设您的工作表如下所示

将此代码粘贴到模块中

Option Explicit

Sub Sample()
    Dim ws As Worksheet
    Dim rngHide As Range
    Dim FoundIt As Long, i As Long, lRow As Long
    Dim SearchString As String

    '~~> Your search string
    SearchString = "Apple"

    '~~> Change this to the relevant sheet
    Set ws = Sheet1

    '~~> Find the last row
    ' https://stackoverflow.com/questions/11169445/error-in-finding-last-used-cell-in-excel-with-vba
    lRow = ws.Range("A" & ws.Rows.Count).End(xlUp).Row

    '~~> Loop through 4 to last row to find the search string
    For i = 4 To lRow
        On Error Resume Next
        FoundIt = Application.WorksheetFunction.Match(SearchString, ws.Rows(i), 0)
        On Error GoTo 0

        '~~> Create a range which needs to be hidden
        If FoundIt = 0 Then
            If rngHide Is Nothing Then
                Set rngHide = ws.Rows(i)
            Else
                Set rngHide = Union(rngHide, ws.Rows(i))
            End If
        End If
        FoundIt = 0
    Next i

    '~~> Hide it if applicable
    If Not rngHide Is Nothing Then rngHide.EntireRow.Hidden = True
End Sub
我已经对代码进行了注释,所以您在理解它时应该不会有问题。但如果你这么做了,那就直接问吧

行动中

您不能使用.AutoFilter进行此操作,但可以使用一个小的vba代码实现您想要的功能

假设您的工作表如下所示

将此代码粘贴到模块中

Option Explicit

Sub Sample()
    Dim ws As Worksheet
    Dim rngHide As Range
    Dim FoundIt As Long, i As Long, lRow As Long
    Dim SearchString As String

    '~~> Your search string
    SearchString = "Apple"

    '~~> Change this to the relevant sheet
    Set ws = Sheet1

    '~~> Find the last row
    ' https://stackoverflow.com/questions/11169445/error-in-finding-last-used-cell-in-excel-with-vba
    lRow = ws.Range("A" & ws.Rows.Count).End(xlUp).Row

    '~~> Loop through 4 to last row to find the search string
    For i = 4 To lRow
        On Error Resume Next
        FoundIt = Application.WorksheetFunction.Match(SearchString, ws.Rows(i), 0)
        On Error GoTo 0

        '~~> Create a range which needs to be hidden
        If FoundIt = 0 Then
            If rngHide Is Nothing Then
                Set rngHide = ws.Rows(i)
            Else
                Set rngHide = Union(rngHide, ws.Rows(i))
            End If
        End If
        FoundIt = 0
    Next i

    '~~> Hide it if applicable
    If Not rngHide Is Nothing Then rngHide.EntireRow.Hidden = True
End Sub
我已经对代码进行了注释,所以您在理解它时应该不会有问题。但如果你这么做了,那就直接问吧

行动中


这两个宏更基本,但完成的任务与Sid的答案相同

第一个宏在范围内循环并检查当前行的前三个单元格中是否有搜索文本,如果在任何单元格中找到,它将循环到下一行。如果没有单元格包含搜索文本,则该行将被隐藏

Dim ws As Worksheet: Set ws = ThisWorkbook.Sheets("Sheet1") 'Define your worksheet
Dim UserSearch As String: UserSearch = ws.Range("A2").Value 'Assign the range for the user entry, change as needed

    For Each cel In ws.Range("A4", ws.Cells(ws.Rows.Count, 1).End(xlUp)) 'Loop through the range
        'Using (= and Or) test if any of the first three cells in the current row contain the search text
        If cel.Value = UserSearch Or cel.Offset(, 1).Value = UserSearch Or cel.Offset(, 2).Value = UserSearch Then
            'If the search text is found in any of the cells then loop to the next row
        Else
            'If the search text is not in any of the cells then hide the row
            cel.EntireRow.Hidden = True
        End If
    Next cel
第二个宏循环遍历范围并检查当前行的前三个单元格中的搜索文本,如果未找到,则该行将隐藏

Dim ws As Worksheet: Set ws = ThisWorkbook.Sheets("Sheet1") 'Define your worksheet
Dim UserSearch As String: UserSearch = ws.Range("A2").Value 'Assign the range for the user entry, change the range as needed

    For Each cel In ws.Range("A4", ws.Cells(ws.Rows.Count, 1).End(xlUp)) 'Loop through the range
        'Using (<> and And) test the first three cells in the current row
        If cel.Value <> UserSearch And cel.Offset(, 1).Value <> UserSearch And cel.Offset(, 2).Value <> UserSearch Then
            'If the search text is not found hide the current row
            cel.EntireRow.Hidden = True
        End If
    Next cel

这两个宏更基本,但完成的任务与Sid的答案相同

第一个宏在范围内循环并检查当前行的前三个单元格中是否有搜索文本,如果在任何单元格中找到,它将循环到下一行。如果没有单元格包含搜索文本,则该行将被隐藏

Dim ws As Worksheet: Set ws = ThisWorkbook.Sheets("Sheet1") 'Define your worksheet
Dim UserSearch As String: UserSearch = ws.Range("A2").Value 'Assign the range for the user entry, change as needed

    For Each cel In ws.Range("A4", ws.Cells(ws.Rows.Count, 1).End(xlUp)) 'Loop through the range
        'Using (= and Or) test if any of the first three cells in the current row contain the search text
        If cel.Value = UserSearch Or cel.Offset(, 1).Value = UserSearch Or cel.Offset(, 2).Value = UserSearch Then
            'If the search text is found in any of the cells then loop to the next row
        Else
            'If the search text is not in any of the cells then hide the row
            cel.EntireRow.Hidden = True
        End If
    Next cel
第二个宏循环遍历范围并检查当前行的前三个单元格中的搜索文本,如果未找到,则该行将隐藏

Dim ws As Worksheet: Set ws = ThisWorkbook.Sheets("Sheet1") 'Define your worksheet
Dim UserSearch As String: UserSearch = ws.Range("A2").Value 'Assign the range for the user entry, change the range as needed

    For Each cel In ws.Range("A4", ws.Cells(ws.Rows.Count, 1).End(xlUp)) 'Loop through the range
        'Using (<> and And) test the first three cells in the current row
        If cel.Value <> UserSearch And cel.Offset(, 1).Value <> UserSearch And cel.Offset(, 2).Value <> UserSearch Then
            'If the search text is not found hide the current row
            cel.EntireRow.Hidden = True
        End If
    Next cel

首先,如果一行有多个苹果,你无论如何都会过滤掉它,对吧,为什么你需要同时过滤呢?其次,从技术上讲,您不能在Excel中同时进行筛选。无论如何,我要做的是先找到要过滤掉的行,然后再过滤它们-你能给出一个数据的例子,以及你希望如何过滤它吗?AutoFilter正按照您的要求进行操作,因此您可能需要一种不同的方法来实现所需的结果。您可以使用帮助器列。您不能使用.AutoFilter进行此操作,但可以使用一个小的vba代码实现所需的功能。首先,如果一行有多个苹果,您无论如何都会将其过滤掉,为什么需要同时进行过滤?其次,从技术上讲,您不能在Excel中同时进行筛选。无论如何,我要做的是先找到要过滤掉的行,然后再过滤它们-你能给出一个数据的例子,以及你希望如何过滤它吗?AutoFilter正按照您的要求执行,因此您可能需要不同的方法来实现所需的结果。您可以使用帮助器列。您不能使用。AutoFilter实现此目的,但可以使用一个小的vba代码来实现所需的功能Hanks Siddharth,它工作得非常完美。然而,最后我创建了另一个列,并使用concat函数合并感兴趣的列并重新粘贴为值,这样我就可以使用一行简单的代码和.autofilter来解决这个问题。出于好奇,您将如何编写“清除”按钮来撤消上面编写的代码?Cells.EntireRow.Hidden=false使用concat是个坏主意。它会给你假阳性。例如,一个单元格中有单词appleton或任何其他包含文本apple的单词,那么它将给出错误的结果。我上面给出的代码将与完全匹配的Hanks Siddharth一起工作,它工作得非常完美。然而,最后我创建了另一个列,并使用concat函数合并感兴趣的列并重新粘贴为值,这样我就可以使用一行简单的代码和.autofilter来解决这个问题。出于好奇,您将如何编写“清除”按钮来撤消上面编写的代码?Cells.EntireRow.Hidden=false使用concat是个坏主意。它会给你假阳性。例如,一个单元格中有单词appleton或任何其他包含文本apple的单词,那么它将给出错误的结果。我上面给出的代码将在 精确匹配