【发布时间】:2017-08-29 11:45:39
【问题描述】:
我经常需要在 Excel 中使用公式搜索单元格中的某些特殊文本。我需要搜索的行数是 100.000 到 500.000,在极少数情况下高达 1.000.000。为了避免长公式,我编写了自己的 UDF 来搜索单元格中的多个文本字符串。新公式很容易处理。我尽我所能优化这个公式的运行时间。 500.000 行需要 11 到 12 秒。
我以两种方式制作这个公式:一种使用 IF 语句 (SuchenSIF),另一种 (SuchenSSELCASE) 使用 SELECT CASE 语句。布斯公式具有相同的速度。你能给我一些提示如何获得更好的性能吗?
这个公式的语法是:
SuchenSIF(要搜索的单元格,要搜索的文本 1,要搜索的文本 6)
SuchenSSELCASE(cell to search, text to search 1, ... text to search 6)
Public Function SuchenSIF(Zelle As Range, such1 As String, Optional such2 As String, Optional such3 As String, Optional such4 As String, Optional such5 As String, Optional such6 As String) As Integer
Application.Volatile
' this code, based on IF-statements need 11-12 seconds for 500.000 rows
' Start of IF-Section
'
ZelleWert = Zelle.Value
SuchenS = InStr(1, ZelleWert, such1, vbTextCompare)
If SuchenS > 0 Then Exit Function
SuchenS = InStr(1, ZelleWert, such2, vbTextCompare)
If SuchenS <> vbFalse Then Exit Function
If Len(such3) > 0 Then
SuchenS = InStr(1, ZelleWert, such3, vbTextCompare)
If SuchenS > 0 Then Exit Function
If Len(such4) > 0 Then
SuchenS = InStr(1, ZelleWert, such4, vbTextCompare)
If SuchenS > 0 Then Exit Function
If Len(such5) > 0 Then
SuchenS = InStr(1, ZelleWert, such5, vbTextCompare)
If SuchenS > 0 Then Exit Function
If Len(such6) > 0 Then
SuchenS = InStr(1, ZelleWert, such6, vbTextCompare)
If SuchenS > 0 Then Exit Function
End If
End If
End If
End If
'
' End of IF-Section
If SuchenS = 0 Then SuchenS = False
End Function
Public Function SuchenSSELCASE(Zelle As Range, such1 As String, Optional such2 As String, Optional such3 As String, Optional such4 As String, Optional such5 As String, Optional such6 As String) As Integer
Application.Volatile
' this code, based on SELECT-CASE-statements need 11-12 seconds for 500.000 rows
' Start of SELECT-CASE -Section
'
ZelleWert = Zelle.Value
SuchenS = InStr(1, ZelleWert, such1, vbTextCompare) * Len(such1)
Select Case SuchenS
Case 0
SuchenS = InStr(1, ZelleWert, such2, vbTextCompare) * Len(such2)
Select Case SuchenS
Case 0
SuchenS = InStr(1, ZelleWert, such3, vbTextCompare) * Len (such3)
Select Case SuchenS
Case 0
SuchenS = InStr(1, ZelleWert, such4, vbTextCompare) * Len(such4)
Select Case SuchenS
Case 0
SuchenS = InStr(1, ZelleWert, such5, vbTextCompare) * Len(such5)
Select Case SuchenS
Case 0
SuchenS = InStr(1, ZelleWert, such6, vbTextCompare) * Len(such6)
Select Case SuchenS
Case 0
Case Else
SuchenS = SuchenS / Len(such6)
Exit Function
End Select
Case Else
SuchenS = SuchenS / Len(such5)
Exit Function
End Select
Case Else
SuchenS = SuchenS / Len(such4)
Exit Function
End Select
Case Else
SuchenS = SuchenS / Len(such3)
Exit Function
End Select
Case Else
SuchenS = SuchenS / Len(such2)
Exit Function
End Select
Case Else
SuchenS = SuchenS / Len(such1)
Exit Function
End Select
'
' End of SELECT-CASE -Section
If SuchenS = 0 Then SuchenS = False
End Function
【问题讨论】:
-
你是从 VBS
Sub调用这个Function吗?还是来自工作表中的单元格? -
我从工作表中的单元格调用它
-
@Enrico,如果这是有效的代码,您应该将此问题提交给代码审查 - 他们在那里很棒
-
为什么要让函数变得易失?它似乎不需要它。
vbTextCompare比将值转换为相同大小写要慢。 -
我建议改用 Excel 公式。 VBA仅限一个线程,但Excel公式可以并行计算msdn.microsoft.com/en-us/library/bb687899.aspx
标签: vba excel excel-formula user-defined-functions