【问题标题】:Not all dates are recognised by VBA并非所有日期都被 VBA 识别
【发布时间】:2018-04-18 20:25:41
【问题描述】:

我正在编写一个自动检查单元格(在 K 列中)是否包含日期的代码。只有当 K 列不包含日期并且 L 列中的日期超过 30 天时,它才会给出错误。

我发现我的代码有效,但并非适用于所有日期。所以我Debug.print 看到他只是忽略了不满足if 要求的事实。我从来没有经历过。

这是代码(在它下面你会找到调试)

Aantal = 0
i = 0
LastRow = 0
k = 0
LastRow = ThisWorkbook.Sheets("Acknowledgements follow up").Range("A1").End(xlDown).Row
'For i = 2 To LastRow
For i = 22214 To 22222
Debug.Print ActiveWorkbook.Sheets("Acknowledgements follow up").Range("L" & i).Value & "      " & ActiveWorkbook.Sheets("Acknowledgements follow up").Range("K" & i) + 30 & "      "; Date & vbCrLf
    If ActiveWorkbook.Sheets("Acknowledgements follow up").Range("L" & i).Value = "" And ActiveWorkbook.Sheets("Acknowledgements follow up").Range("K" & i) + 30 > Date Then
    Aantal = Aantal + 1
    MsgString = MsgString & i & " / "
    End If
Next i
If MsgString <> "" Then MsgString = Left(MsgString, Len(MsgString) - 3)

If Aantal > 1 Then
MsgBoxAnswer = MsgBox("There are " & Aantal & " dates missing in the acknowlegement sheet" & vbCrLf _
& "The missing dates are on rows " & MsgString, vbOKOnly + vbExclamation, "Missing dates")
End If

If Aantal = 1 Then
MsgBoxAnswer = MsgBox("There is " & Aantal & " date missing in the acknowlegement sheet" & vbCrLf _
& "The missing date is on row " & MsgString, vbOKOnly + vbExclamation, "Missing dates")
End If

我发现单元格 22217 包含一个他应该给出错误的案例。但他没有,整个文档包含超过 29000 行。它给了我 58 个错误,但实际上还有更多。

这是我得到的调试信息(检查日期是否为空(L 列)/K 列 + 30 天/今天)

05-08-13 01-09-13 06-11-17

05-08-13 01-09-13 06-11-17

05-08-13 01-09-13 06-11-17

 01-09-13      06-11-17

05-08-13 04-09-13 06-11-17

06-08-13 04-09-13 06-11-17

05-08-13 04-09-13 06-11-17

05-08-13 04-09-13 06-11-17

30-12-13 04-09-13 06-11-17

如您所见,它识别出第 22217 行为空且日期超过 30 天。所以应该触发。我发现是这条线不能正常工作:ActiveWorkbook.Sheets("Acknowledgements follow up").Range("K" &amp; i) + 30 &gt; Date

有什么想法吗? 谢谢! 川流

【问题讨论】:

  • 这段代码所做的只是检查单元格中是否有日期???
  • 粘贴出了点问题 :) 我修好了
  • @cxw 检查 L 列是否为空以及 K 列是否超过 30 天。如果满足这两个要求,它应该会弹出一个窗口。由于某种原因它没有。我已经在我的描述中修复了它。谢谢指出!
  • 因为你没有 MsgBox MsgString
  • KawaRu:测试 Kx + 30 &gt; Date 正在测试 K 列中的值是否在过去 30 天内内,而不是在 超过 30 天。 Kx &lt; (Date-30) 将测试超过 30 天。你要哪个?

标签: vba excel date if-statement


【解决方案1】:

这适用于我的系统,用于测试超过 30 天的日期

Option Explicit ' Always start every VBA file with this
Option Base 0   ' Not as important, but I use it as a reminder to myself

Public Sub KawaRu()
    Dim CL As Long, CK As Long  ' Column numbers for L, K
    CL = AscW("L") - AscW("A") + 1
    CK = AscW("K") - AscW("A") + 1

    ' Always Dim your variables, and use Option Explicit
    Dim aantal As Long, i As Long, LastRow As Long, k As Long
    Dim MsgString As String
    aantal = 0
    i = 0
    k = 0

    ' Avoid repeating references to objects.  Instead, save them in a variable.
    Dim sh As Worksheet
    Set sh = ActiveWorkbook.Sheets("Acknowledgements follow up")

    LastRow = sh.Range("A1").End(xlDown).Row

    For i = 1 To LastRow
        Debug.Print sh.Range("L" & i).Value, sh.Range("K" & i) + 30, Date
        ' Use Cells() for speed when you're in a loop.
        If sh.Cells(i, CL).Value = "" And _
                sh.Cells(i, CK) < (Date - 30) Then
              ' ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ older than 30 days
            aantal = aantal + 1
            MsgString = MsgString & i & " / "
        End If
    Next i

    Debug.Print aantal
    If MsgString <> "" Then MsgString = Left(MsgString, Len(MsgString) - 3)

    Dim MsgBoxAnswer As VbMsgBoxResult

    If aantal > 1 Then
        MsgBoxAnswer = MsgBox("There are " & aantal & " dates missing in the acknowlegement sheet" & vbCrLf _
            & "The missing dates are on rows " & MsgString, vbOKOnly + vbExclamation, "Missing dates")
    End If

    If aantal = 1 Then
        MsgBoxAnswer = MsgBox("There is " & aantal & " date missing in the acknowlegement sheet" & vbCrLf _
        & "The missing date is on row " & MsgString, vbOKOnly + vbExclamation, "Missing dates")
    End If

End Sub

我的测试数据是:

col. A       K              L             M
x            5/8/2013       1/9/2013      6/11/2017
x            1/9/2013                     6/11/2017
x            1/9/2013                     6/11/2017
x            11/1/2017                    6/11/2017

我得到的结果是:

There are 2 dates missing in the acknowledgement sheet
The missing dates are on rows 2/ 3

编辑

算法问题是日期测试。 Kx + 30 &gt; Date 测试 K 列中的值是否在过去 30 天内,不超过 30 天。在上面的代码中,Kx &lt; (Date - 30) 测试超过 30 天。 (Kx + 30) &lt; Date(小于)也会这样做。

对上述代码的改进是重命名CKCL。不要以它们的位置来命名它们,而是以它们的含义来命名它们。例如,COL_ACK_RECEIVED 或其他东西。这将使您在稍后返回时更容易理解您的代码。

编辑 2

  • 正如 @HarassedDad 在评论中指出的那样,请注意 d/m/y 与 m/d/y 以及其他日期格式问题。
  • “超过 30 天”可能表示 &lt; Date - 30&lt;= Date - 30,具体取决于您的要求。
  • 对于可能正在考虑改编此内容的未来读者,请记住“30 天前”和“上个月”是非常不同的!
  • This answer 关于Range.Value 是一个很好的。我要补充一点,使用 CStr() 或其他转换器函数是一个很好的做法,因为 Range.Value 返回一个 Variant。
  • This questionthis question,以及他们的答案,都很好读。为什么= "" 可能并不总是匹配看起来为空的单元格。

【讨论】:

  • 这确实有效!谢谢,仍然不确定我的代码出了什么问题,因为它适用于某些行。感谢您的提示,我会记住的:)祝您有美好的一天!
  • 请记住 01-09-13 是 2013 年 9 月 1 日或 2013 年 1 月 9 日。而且 Excel 不会始终以相同的方式解释日期。 (实际上,根据您的本地设置,在某些情况下可能会将其解释为 2001 年 9 月 13 日)
  • 我希望我能两次支持这个答案。实际上,我希望所有 SO 回答者都在他们的帖子中付出尽可能多的努力!让他们继续前进!
  • @Mat'sMug 感谢您的客气话和鼓励!非常感谢。
猜你喜欢
  • 1970-01-01
  • 2011-06-07
  • 1970-01-01
  • 1970-01-01
  • 2023-04-09
  • 1970-01-01
  • 2012-06-11
  • 2014-10-17
  • 2021-06-06
相关资源
最近更新 更多