2014-10-17 245 views
0

我有通過文件查找日期的代碼,但它沒有返回,它發現匹配我的正則表達式。正則表達式,找不到匹配

CODE:

std::string s(line); 
std::smatch m; 
std::regex e("^[0,1]?\d{1}\/(([0-2]?\d{1})|([3][0,1]{1}))\/(([1]{1}[9]{1}[9]{1}\d{1})|([2-9]{1}\d{3}))$"); 
std::cout << "Target sequence: " << s << std::endl; 
std::cout << "Regular expression: ^[0,1]?\d{1}\/(([0-2]?\d{1})|([3][0,1]{1}))\/(([1]{1}[9]{1}[9]{1}\d{1})|([2-9]{1}\d{3}))$" << std::endl; 
std::cout << "The following matches and submatches were found:" << std::endl; 

while (std::regex_search(s, m, e)) { 
    for (auto x : m) std::cout << x << " "; 
    std::cout << std::endl; 
    s = m.suffix().str(); 
} 

OUTPUT:

Success 
Target sequence: 12/28/2002  2 15 38 43 50 
Regular expression: ^[0,1]?d{1}/(([0-2]?d{1})|([3][0,1]{1}))/(([1]{1}[9]{1}[9]{1 
}d{1})|([2-9]{1}d{3}))$ 
The following matches and submatches were found: 
Enter q to quit: 

是我的正則表達式不正確或者是別的東西嗎?

+0

不能解決的東西,但只是您正則表達式的簡化:??'^ [0,1] \ d \ /(([0-2] \ d)|(3 [0,1]) )\ /((199 \ d)|([2-9] \ d {3}))$' – nhahtdh 2014-10-17 02:13:44

+0

@nhahtdh謝謝 – 2014-10-17 02:22:54

回答

3

的原因是在你的正則表達式和如何指定字符串文字:

  • 之前,我們做任何修正你的正則表達式,嘗試打印出來的字符串文字到控制檯:

    std::cout << "^[0,1]?\d{1}\/(([0-2]?\d{1})|([3][0,1]{1}))\/(([1]{1}[9]{1}[9]{1}\d{1})|([2-9]{1}\d{3}))$"; 
    

    你會看到\丟失,並且<regex>看不到它們。

    要在字符串中指定\,您需要轉義它,\\

    順便說一句,打印字符串是語言中的調試步驟之一,其中沒有專門的RegExp文字,並且必須通過字符串完成構造。

  • 您正在使用^$來錨定您的搜索。如果日期自己排成一行,它只會找到一個匹配,並且一定不能有前導或尾隨空格。

  • 你有很多冗餘的語法,例如[1]{1}或。可以取出單個字符的字符類(它不是正則表達式中的特殊字符),即1{1}。並{1}總是冗餘,即[1]{1}可以縮短爲1

  • /無需在字符串文字或正則表達式中轉義。

  • 上述固定和刪除^$句法問題:

    "[0,1]?\\d/(([0-2]?\\d)|(3[0,1]))/((199\\d)|([2-9]\\d{3}))" 
    
  • 通過[0,1],你可能想[01]。如果要匹配字符AB,請將它們放在字符類[AB]中彼此相鄰的位置。您的[0,1]也將匹配逗號,

  • 您可以將()放入([0-2]?\\d),(3[0,1])。年份相同。外部捕獲組已經足夠了。

  • 運用2點上方:

    "[01]?\\d/([0-2]?\\d|3[01])/(199\\d|[2-9]\\d{3})" 
    

,當你想提取數據的正則表達式應該現在的工作,但不是很好,如果你想用它來驗證。我不知道爲什麼你把這一年限制在1990年到9999年,但這可能是你的商業邏輯。

+0

非常感謝您的詳細解釋。我不知道如何編寫正則表達式,這是我第一次使用正則表達式,而且我幾乎對它們一無所知。我只是從谷歌複製這個表達式。你知道哪些資源我可以瞭解它們嗎?另外,我不希望它被限制在1990到9999之間,我該如何解決這個問題?再次謝謝你。 – 2014-10-17 03:01:01

+0

@DaveCribbs:這一年你想要什麼樣的範圍?至於資源,如果是C++,請檢查ECMA/JavaScript RegExp(因爲C++中的正則表達式基於它)** first **,然後檢查http://stackoverflow.com/questions/22937618/reference-what-does -this-regex-mean/22944075#22944075如果你需要更深入的解釋。 – nhahtdh 2014-10-17 03:04:56

+0

有沒有辦法讓它接受任何一年,還是必須有規範? – 2014-10-17 03:09:29