我有一列包含.cpp文件名列表,另一列表示测试用例。我想搜索工作表中与测试用例字符串匹配的所有行,并打印该行的文件名。
column 1 column2
-------- ------------
file1.cpp testcase1
file2.cpp testcase1
file3.cpp testcase3
... .......
.... .......
所以最后我想要一个看起来像这样的输出:
Testcase1 Testcase2
file4.cpp file5.cpp
file9.cpp file8.cpp
file5.cpp file13.cpp
这是vba代码:
Function fileToTest(Search_string As String, _
Search_in_col As Range)
Dim result As String
Dim i As Long
Dim j As Long
Dim rArray(20) As String
Dim rCnt As Long
Dim rTmp As String
Dim found As Long
Dim testCases, Value As Variant
Dim currentRow As Long
Dim fCnt As Long
For i = 1 To Search_in_col.Count 'search each test case column
testCases = Split(Search_in_col.Cells(i, 1), ";")
For Each Value In testCases
If Search_string = Value Then
ActiveCell.Value = Search_in_col.Cells(i, 2).Value
' write the next row after active cell. not sure how to do this
End If
Next Value
Next i
End Function
当我尝试写入ActiveCell.Value
时,该函数失败答案 0 :(得分:0)
您面临的问题是 - 根据您的评论 - 您需要用户定义的功能 - 但随后尝试修改工作表。这是不可能的,因为UDF的体系结构是您不能将任何内容更改为工作表,而只返回您的函数的值 - 然后显示该值。此外,在UDF中,通常不允许读取任何其他单元格的值而不是作为参数移交的单元格的值 - 否则这将导致Excel认为某处存在循环引用。
因此,我看到以下三个选项:
以下是详细信息:
<强> 1。修改您的UDF
假设您在A1中输入'testcase1',构建一个可以像这样调用的UDF:
=FileToTestCase(A1,1,SourceSheet!A2:A100,SourceSheet!B2:B100)
UDF的VBA定义将是这样的:
Public Function FileToTestCase(sTestCaseName as String, iElementNumber as Integer, _
rngFileNames as Range, rngTestcases as Range) as String
CodeToFigure out the iElementNumer_th entry for sTestCaseName
FileToTestCase = YourResult
End Function
然而,这种方法非常低效,因为您每次都需要解析源列表。您可以使用在第一次调用中初始化并稍后使用的一些内部模块范围变量加快速度 - 但是您需要注意检测更改。或者,您可以使用一个大数组公式。但是,这两种方法都付出了相当大的努力。
<强> 2。创建一个宏,用于填充所有单元格
而不是UDF,你有一个宏可以在一次冲动中填充所有单元格。如果要自动更新内容,请在每次源数据更改时从Worksheet_Change事件中调用宏。
此代码应执行此操作:
Sub FillTestcases(rngFiles As Range, rngTestcases As Range, rngStartResult As Range)
Dim d As New Scripting.Dictionary
Dim lRow As Long
Dim sTestCase As Variant
Dim sFile As Variant
Dim rngResult As Range
Const csSeparator As String = "|"
For lRow = 1 To rngFiles.Rows.Count
sTestCase = rngTestcases(lRow, 1).Value
sFile = rngFiles(lRow, 1).Value
If d.Exists(sTestCase) Then
d(sTestCase) = d(sTestCase) & csSeparator & sFile
Else
d.Add sTestCase, sFile
End If
Next
Set rngResult = rngStartResult
For Each sTestCase In d.Keys
rngResult.Value = sTestCase
rngResult.Font.Bold = True
lRow = 1
For Each sFile In Split(d(sTestCase), csSeparator)
rngResult.Offset(lRow) = sFile
lRow = lRow + 1
Next sFile
Set rngResult = rngResult.Offset(, 1)
Next sTestCase
End Sub
请注意,您需要添加对 Microsoft Scripting Runtime 的引用才能使用Dictionary类。另请注意,此代码不会合并重复项,因此您可能需要进行调整。
第3。仅使用Excel公式
假设您的文件名在A1:A10中,B1:B10中的测试用例和测试用例名称列表在第1行,从F列开始,在F2中使用此公式:
=IFERROR(INDEX($A$1:$A$10,-INT((LARGE(($B$1:$B$10=F$1)-ROW($B$1:$B$10)/10000,ROW(F1))-1)*10000)),"")
这是一个数组公式,所以输入 Ctrl - Shift - 输入。
HTH!