Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/excel/25.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/list/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Excel中的VBA搜索多个选项卡上的字符串并返回位置_Excel_Excel 2010_Vba - Fatal编程技术网

Excel中的VBA搜索多个选项卡上的字符串并返回位置

Excel中的VBA搜索多个选项卡上的字符串并返回位置,excel,excel-2010,vba,Excel,Excel 2010,Vba,我已经形成了代码进行搜索的问题是试图让它找到多个结果。当前,它将返回每个选项卡上字符串的第一个位置,但随后将继续。当我实现当前注释掉的While循环时,它似乎找到了第一个结果,然后转义循环 我不确定VBA循环是否有我遗漏的怪癖,或者我的while检查不太正确,但我尝试过通过分解它并使用消息框进行调试,但除了缩小我认为while循环代码中存在的问题之外,没有任何效果 Public Function GetSearchArray(strSearch As String) As String Dim

我已经形成了代码进行搜索的问题是试图让它找到多个结果。当前,它将返回每个选项卡上字符串的第一个位置,但随后将继续。当我实现当前注释掉的While循环时,它似乎找到了第一个结果,然后转义循环

我不确定VBA循环是否有我遗漏的怪癖,或者我的while检查不太正确,但我尝试过通过分解它并使用消息框进行调试,但除了缩小我认为while循环代码中存在的问题之外,没有任何效果

Public Function GetSearchArray(strSearch As String) As String
Dim strResults As String
Dim SHT As Worksheet
Dim rFND As Range
Dim sFirstAddress As Range
For Each SHT In ThisWorkbook.Worksheets
    'MsgBox "Looping over worksheets"
    Set rFND = Nothing

    With SHT.UsedRange
        'MsgBox "Searching for" & strSearch

        Set rFND = .Cells.Find(What:="*" & strSearch & "*", LookIn:=xlValues, LookAt:=xlPart, SearchOrder:=xlRows, SearchDirection:=xlNext, MatchCase:=False)
        If Not rFND Is Nothing Then

            'Save first result so we can exit the loop
            If sFirstAddress Is Nothing Then
                MsgBox "We have a result and sFirstAddress is nothing"
                Set sFirstAddress = rFND
            End If


            'Need to loop within the sheet to keep finding results
            'While (Not rFND Is Nothing) And rFND <> sFirstAddress

                'Deal with the results and build a string
                If strResults = "" Then
                    'MsgBox "No prev results"
                    strResults = "Worksheet(" & SHT.Index & ").Range(" & Chr(34) & rFND.Address & Chr(34) & ")"
                    MsgBox "First result " & strResults
                Else
                    strResults = strResults & "|" & "Worksheet(" & SHT.Index & ").Range(" & Chr(34) & rFND.Address & Chr(34) & ")"
                    MsgBox strResults
                End If

                Set rFND = .FindNext(rFND)


           'Wend

        End If
    End With
MsgBox "End sheet loop.."
Next
MsgBox "Finished going over sheets"
MsgBox strResults
End Function
公共函数GetSearchArray(strSearch作为字符串)作为字符串
作为字符串的Dim strresult
将SHT变暗为工作表
弱rFND As范围
Dim sFirstAddress作为范围
用于此工作簿中的每个SHT。工作表
“MsgBox”在工作表上循环
设置rFND=Nothing
使用SHT.UsedRange
“MsgBox”正在搜索“&strSearch”
Set rFND=.Cells.Find(What:=“*”&strearch&“*”,LookIn:=xlValues,LookAt:=xlPart,SearchOrder:=xlRows,SearchDirection:=xlNext,MatchCase:=False)
如果不是,那么rFND什么都不是
'保存第一个结果,以便退出循环
如果sFirstAddress不算什么,那么
MsgBox“我们有一个结果,sFirstAddress什么都不是”
设置sFirstAddress=rFND
如果结束
'需要在工作表中循环以不断查找结果
'While(非rFND为Nothing)和rFND sFirstAddress
'处理结果并生成字符串
如果strResults=“”,则
'MsgBox“没有上一个结果”
strResults=“工作表(“&SHT.Index&”)范围(“&Chr(34)&rFND.Address&Chr(34)&”)”
MsgBox“第一个结果”和strResults
其他的
strResults=strResults&“|”和“工作表(&SHT.Index&”)范围(&Chr(34)&rFND.Address&Chr(34)&”)
MsgBox strResults
如果结束
设置rFND=.FindNext(rFND)
“温德
如果结束
以
MsgBox“结束页循环…”
下一个
MsgBox“已完成检查表单”
MsgBox strResults
端函数

您需要循环回到
Set rFND=.Cells.Find(What:=“*”&strearch&“*”,LookIn:=xlValues,LookAt:=xlPart,SearchOrder:=xlRows,SearchDirection:=xlNext,MatchCase:=False)
代码到达
之前的行,而
循环,目前不会发生,并且rFND始终等于sFirstAddress

我不确定存储地址结果并在循环时检查它们的最有效方法,但我相信有人可以帮助您完成最后一部分。我认为应该将每个结果存储在一个数组中,并对照数组检查每个新结果,直到没有找到新结果,然后转到下一页


您可能还必须将Find命令更改为从上次找到的结果开始,如果它每次都在同一个位置开始,我认为它会一次又一次地找到相同的结果。我不确定,我没有找到太多。

像这样的东西应该适合你:

Public Function GetSearchArray(strSearch As String) As String

    Dim ws As Worksheet
    Dim rngFound As Range
    Dim strFirst As String
    Dim strWSname As String

    For Each ws In ActiveWorkbook.Sheets
        Set rngFound = ws.UsedRange.Find(strSearch, ws.UsedRange.Cells(ws.UsedRange.Cells.Count), xlValues, xlPart)
        If Not rngFound Is Nothing Then
            strWSname = ws.Name
            If InStr(1, ws.Name, " ", vbTextCompare) > 0 Then strWSname = "'" & strWSname & "'"
            strFirst = rngFound.Address
            Do
                GetSearchArray = GetSearchArray & "|" & strWSname & "!" & rngFound.Address
                Set rngFound = ws.UsedRange.Find(strSearch, rngFound, xlValues, xlPart)
            Loop While rngFound.Address <> strFirst
        End If
    Next ws

    If Len(GetSearchArray) > 0 Then GetSearchArray = Mid(GetSearchArray, 2)

End Function

不While循环将被完全跳过。
(非rFND即无)
部分将得到满足,但
rFND sFirstAddress
将不会得到满足。你在它们之间使用了
,因此因为两者都不满意,它直接转到WEnd并继续。哈,对不起,你的无限循环问题消失了,你一定找到了答案:)对不起,我意识到我的评论不正确,所以删除了它。如你所说。:)我想我会改变代码的工作方式。在上一次迭代中,我只是在一张表中查找外观的计数。我想我会合并这个,然后调用find x多次,而不是上面的while循环。看起来这样可以工作。祝你好运对不起,还没有人告诉你一个有效的方法。当你改变你的问题时,我建议保留旧代码,把你的新试用版放在下面,以防有人能让While循环比Count循环工作得更好。这正是我想要的。一个扩展-如何从单元格调用它并将输出返回到单元格中?我尝试了调用重写的第二个函数,但它不起作用。在一个单元格中:
=GetSearchArray(“test”)
如果你想用“|”以外的东西来分隔结果,你可以使用替换项,比如:
=SUBSTITUTE(GetSearchArray(“test”),“|”,”,”)
嗯,我试过了,但单元格只是出错并显示了#值!我试着通过按Ctr+Shift+Enter来确保它是一个数组公式,但运气不好。结果表明,在UDF中不能使用
Range.FindNext
方法,这就是导致问题的原因。我使用了一个带有
Range.Find
方法的替代方法,然后为我成功地测试了它。请参阅更新的答案
Sub tgr()

    MsgBox Replace(GetSearchArray("test"), "|", Chr(10))

End Sub