使用 Vlookup 或 VBA 从多个单个单元格中获取特定数据

使用 Vlookup 或 VBA 从多个单个单元格中获取特定数据

我有一个奇怪的问题。我将数据从应用程序中提取到 Excel 电子表格中,以进行一些高级分析。我有一列,称为“历史记录”,它可以在单个单元格内包含多个条目,而不是简单的日期等。以下是一个例子:在此处输入图片描述

这是另一个例子

在此处输入图片描述

我需要的是下面单元格中第一个或最早的时间戳,其中添加了技术/其他审批者(突出显示)。换句话说,就是最底部的那个。我查看了 30 多个记录,这似乎是正确的。有时它只有一个带有时间戳的条目,并且在下面单元格中添加了技术/其他审批者,没有其他数据。这让我抓狂,因为它有我需要的数据,但我无法获取它。

答案1

如果我理解正确的话,下面的代码应该可以工作。正则表达式将返回最后的单元格中的日期(并且必须采用您显示的格式),其中下一个行以短语“技术/其他审批人

Option Explicit
Function LastDate(S As String) As String
    Dim RE As Object, MC As Object

Set RE = CreateObject("vbscript.regexp")
With RE
    .Pattern = "[\s\S]+((?:\d{2}-){2}\d{4}\s(?:\d{2}:){2}\d{2}).*[\n\r]+Technical/other approvers.*"
    .ignorecase = True
    .MultiLine = True
    .Global = False
    If RE.test(S) = True Then
        Set MC = RE.Execute(S)
        LastDate = MC(0).submatches(0)
    End If
End With

End Function

在此处输入图片描述

编辑:(根据 Raystafarian 的建议)上面的代码使用了所谓的后期绑定。如果你只在自己的机器上使用此功能,早期绑定会更好,因为你有优势智能感知输入代码时。如果要分发,可能就没那么简单了,因为您需要在所有收件人的计算机上设置引用。

性能应该会有所改善。但是,这是否明显取决于数据库的大小。

以下是为了利用早期绑定而重写的代码。

Option Explicit
'Using Early Binding
'Set Reference (Tools/References) to Microsoft VBScript Regular Expressions 5.5

Function LastDate2(S As String) As String
    Dim RE As RegExp, MC As MatchCollection

Set RE = New RegExp
With RE
    .Pattern = "[\s\S]+((?:\d{2}-){2}\d{4}\s(?:\d{2}:){2}\d{2}).*[\n\r]+Technical/other approvers.*"
    .ignorecase = True
    .MultiLine = True
    .Global = False
    If RE.test(S) = True Then
        Set MC = RE.Execute(S)
        LastDate2 = MC(0).submatches(0)
    End If
End With

End Function

答案2

简单的做法是使用循环,我更喜欢for循环,但是do until可能效果更好。

Sub Macro1()
Dim searchRange As Range
Dim searchString As String
Dim cellValue As String
Dim myCell As Range
Dim foundCell As Range
Set searchRange = Range("A2:A10")
searchString = "Technical/other approvers"

For Each myCell In searchRange
    cellValue = myCell
    If InStr(cellValue, searchString) Then
        Set foundCell = myCell
        Exit For
    End If
Next
MsgBox "found at " & myCell.Address

Dim myTimeStamp As String
Dim endString As Long
endString = InStr(myCell, " - ")

myTimeStamp = Left(myCell, endString - 1)
MsgBox myTimeStamp

End Sub

当然,如果是我的话,我会

lastRow = cells(rows.count,1).end(xlup).row
dim i as long
for i = 1 to lastRow
  cellValue = cells(i,1)
  ...

相关内容