2017-04-18 36 views
1

我已經開始工作在一個新的工作,事實證明,在一堆目錄中有大量完全無組織,非標準化的文件名(手工工作太多)。最初,我的計劃是使用簡單的VBA腳本來使用前13個字符的字符串比較,如果它們不匹配,則在前面放置一個理想日期格式的字符串(利用文檔創建日期),但那麼我注意到已經存在幾種模式,並且通過執行我原來的計劃,我將在未來創建另一個問題(通過在我的理想字符串後面具有不正確的日期代碼)。因此,經過研究,我意識到正則表達式模式應該是一條走的路。用於日期編碼文檔的VBA正則表達式模式

我的理想出發格式是這樣的: 「YYYY.MM.DD - 」(即「2014年11月20日 - 」我嘗試創建我的第一個表達式匹配這一點,但有到目前爲止沒有運氣:

^[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+ 

是否有人可以告訴我,我錯了?通過網上教程我的搜索已經離開我比當我開始更加困惑。

計劃從那裏來匹配其他常見的日期格式(見下文)中的目錄並將它們替換爲「理想」,任何有助於識別它們的正則表達式都將不勝感激。

「年月月日日」 「月日 - 」 「年月日」 「YYYYMMDD - 」

我的計劃是使用一個簡單的IF VBA函數,發現該名稱相匹配並做neccessary VBA字符串操作來創建正確的標準格式。

例如,如果該文件的當前名稱是這個「141003 XXXXXX」將被替換爲「2014年10月3日 - XXXXX」等

非常感謝您的幫助提前。

+1

使用'([1-2] [0-9])([0-9] [0-9])\(0 [1-9] | 1 [0-2])\(0 [1-9] |。[1-2] [0-9] | 3 [0-1])'如果你想排除誤判,如'2017.13.32' –

回答

2

在你的表情中,你已經放置了由三個點分隔的四位數組。顯然,日期只有三個數字組和兩個點。所以,第一次約會模式的正則表達式是:

^[0-9]{4}\.[0-9]{2}\.[0-9]{2} 

演示:https://regex101.com/r/vUigcj/1

請注意{4}{2}量詞這究竟需要四個和兩個數字分別爲,而不是更寬鬆的「一個或多個數字「由+量詞提供的條件。

一個更通用的正則表達式覆蓋你列出的所有模式是

^(?:[0-9]{2})?[0-9]{2}[ .]?[0-9]{2}[ .]?[0-9]{2} (?:-)? 

演示:https://regex101.com/r/vUigcj/2

說明:

  • ^ - 字符串錨開始
  • (?: - 非捕獲組開始
    • [0-9]{2} - 今年前兩個數字
  • ) - 非捕獲組
  • ?末 - 使這組可選(允許省略世紀位)
  • [0-9]{2} - 最後的一年兩位數
  • [ .] - 空格或點 - 日期分隔符
  • ? - 使這個分隔符可選
  • [0-9]{2} - 月
  • [ .]?的兩位數 - 另一個可選的日期分隔符
  • [0-9]{2} - 一天的兩位數字
  • - 空間(直譯)
  • (?:-)? - 可能後跟破折號和空格
+0

哇,非常感謝你,我試圖讓一個只是代表「 yymmdd - 「那前派。 ^ [0-9] {6}( - ) 這會工作嗎? – MSalty

+1

@MSalty:不客氣!在'^ [0-9] {6} [ - ]'正則表達式中,最好刪除括號(['^ [0-9] {6} - '](https://regex101.com/r/ vUigcj/3)),否則會[失敗](https://regex101.com/r/vUigcj/4)。方括號中的短劃線(除非它是括號中的第一個或最後一個字符)具有特殊含義。它定義了一個範圍(就像在'[0-9]中定義的範圍從'0'到'9')。在'[ - ]'中,短劃線定義了一個從''(空格)到''(空格)的範圍,簡單地說就是「空格」。 –

+0

編輯:我不敢相信我包括一個太多的點集:|今天我的屏幕時間太多了。你是一位出色的老師,謝謝! – MSalty

1

yyyy.mm.dd的模式,例如2014.11.20是:

(^[0-9]{4})(.)([0-9]{2})(.)([0-9]{2}) 

注意:爲RegEx培訓和測試偉大的網站:RegEx101

+0

非常感謝您的網站,它已被證明非常非常方便。 – MSalty

1

下面是一個簡單的VBA函數處理您的所有需求:

Dim regEx As New RegExp 

Function ReplaceDates(text As String, pattern As String, Optional centuryPrefix As String) 
    Dim replacement As String 
    Dim fullMatch As String 

    With regEx 
     .Global = False 
     .MultiLine = True 
     .IgnoreCase = False 
     .pattern = pattern 
    End With 

    If regEx.test(text) Then 
     Set matches = regEx.Execute(text) 
     fullMatch = matches(0).Value 
     replacement = Replace(text, fullMatch, centuryPrefix & matches(0).SubMatches(0) & "." & matches(0).SubMatches(1) & "." & matches(0).SubMatches(2) & " - ") 
     ReplaceDates = replacement 
    End If 
End Function 

Sub test() 
    Dim pattern1 As String 
    Dim pattern2 As String 
    Dim pattern3 As String 

    ' will match "140324 xxx" 
    pattern1 = "^(\d{2})(\d{2})(\d{2})\s" 
    ' will match "2014 03 24 - xxx" 
    pattern2 = "^(\d{4})\s(\d{2})\s(\d{2})\s-\s" 
    ' will match "20140324 xxx" 
    pattern3 = "^(\d{4})(\d{2})(\d{2})\s" 

    Debug.Print ReplaceDates("141024 xxxxxx ", pattern1, "20") 
    Debug.Print ReplaceDates("2014 03 24 - xxxxxx ", pattern2) 
    Debug.Print ReplaceDates("20140324 xxxxxx ", pattern3) 
End Sub 
+0

更新後的解決方案 –

+0

這太棒了,我不確定替換函數是如何工作的,但是您已經完美地對它進行了排序。一旦我明天上班,我會發布我的完整解決方案。 – MSalty

+0

然後考慮一點點upvote會是... cool:D ^^ –