2016-04-11 11 views
3
Bütün düzenli ifade maçları ve konumlarını almak gerekir

her regex maçı teker teker alın.pozisyonları

std::regex r("(a)|(b)|(c)"); 

Ve bu giriş metni:

std::string text("abcab"); 

Şimdi her döngüde orada döngü maçları Bir maçından tüm oluşumlarını erişebilirler istediğiniz Örneğin

, bu regex var . Yani ilk döngüde 0 konumunda "a" ve 3. pozisyonda "a" alabiliyordum. İkinci döngüde 1'de "b", "4" de "b" olacaktı ve üçüncü döngüde "c" olurdu. "2. pozisyonda bunu nasıl yapabilirim?

Şu anda her regex parçasını ayrı ayrı ((a), (b) ve (c) için regex) tek tek takip ediyorum. Ama bunların birçoğu var ki ben daha iyi/daha hızlı bir çözüm arıyorum.

+0

http://en.cppreference.com/w/cpp/regex/regex_iterator –

+0

şey (https://ideone.com/QAqBGn)? –

+0

@ WiktorStribiżew Geçerli maçın hangi eşleşme sayısının olduğunu bilmem gerekiyor. –

cevap

2

Sen yakalanan değerlerini saklamak ve daha sonra eşleşti alternatif hangi dal kontrol etmek dize vektörleri beyan ve ilgili vektöre ekleyebilirsiniz. İşte

bir C++ demo geçerli:

#include <string> 
#include <iostream> 
#include <regex> 
using namespace std; 

int main() { 
    std::regex r("(a)|(b)|(c)"); 
    std::string s = "abcab"; 
    std::vector<std::string> astrings; // Declare the vectors to 
    std::vector<std::string> bstrings; // populate with the contents 
    std::vector<std::string> cstrings; // of capturing groups 

    for(std::sregex_iterator i = std::sregex_iterator(s.begin(), s.end(), r); 
      i != std::sregex_iterator(); 
      ++i) 
    { 
     std::smatch m = *i; 
     if (m[1].matched) {     // Check if Group 1 matched and 
      astrings.push_back(m[1].str()); // Put a value into a string vector 
     } 
     else if (m[2].matched) {   // Check if Group 2 matched and 
      bstrings.push_back(m[2].str()); // Put a value into b string vector 
     } 
     else if (m[3].matched) {    // Check if Group 3 matched and 
      cstrings.push_back(m[3].str()); // Put a value into c string vector 
     } 
    } 

    // Printing vectors - DEMO 
    for (auto i: astrings) 
     std::cout << i << ' '; 
    std::cout << "\n"; 
    for (auto i: bstrings) 
     std::cout << i << ' '; 
    std::cout << "\n"; 
    for (auto i: cstrings) 
     std::cout << i << ' '; 

    return 0; 
} 

Ayrıca Regexp'i (Galik's comment bakınız) bildirirken std::regex_constants::optimize bayrağını kullanmayı düşünebilirsiniz. [Bu] gibi

+1

'u kullanarak optimize etmeyi unutmayın. Teşekkür ederiz. Bu hala çalışıyor, ama ihtiyacım olandan çok yavaş. 60'ın üzerinde regex var ve giriş metni binlerce satır olabilir, bu yüzden başka bir şekilde çözmem gerekiyor. Ama yine de teşekkürler! :) –

+0

Belki de, regex sizin göreviniz için en iyi araç değildir. Ya da, şüphelendiğim gibi, sorun, performans sorunlarına neden olabilecek bir ya da birkaç deseninizde (normal ifadelerle sık karşılaşılan bir sorun) bir yerdedir. –

İlgili konular