Регулярное выражение заменяет шаблон на шаблон
Я новичок в регулярных выражениях. Я гуглил и нашел некоторые решения, а затем я придумал свое собственное решение следующим образом
#include <string.h>
#include <regex.h>
#include <iostream>
int rreplace (char *buf, int size, regex_t *re, char *rp){
char *pos;
int sub, so, n;
regmatch_t pmatch [10];
if (regexec (re, buf, 10, pmatch, 0))
return 0;
for (pos = rp; *pos; pos++)
if (*pos == '\\' && *(pos + 1) > '0' && *(pos + 1) <= '9'){
so = pmatch [*(pos + 1) - 48].rm_so;
n = pmatch [*(pos + 1) - 48].rm_eo - so;
if (so < 0 || strlen (rp) + n - 1 > size)
return 1;
memmove (pos + n, pos + 2, strlen (pos) - 1);
memmove (pos, buf + so, n);
pos = pos + n - 2;
}
sub = pmatch [1].rm_so; /* no repeated replace when sub >= 0 */
for (pos = buf; !regexec (re, pos, 1, pmatch, 0); ){
n = pmatch [0].rm_eo - pmatch [0].rm_so;
pos += pmatch [0].rm_so;
if (strlen (buf) - n + strlen (rp) + 1 > size)
return 1;
memmove (pos + strlen (rp), pos + n, strlen (pos) - n + 1);
memmove (pos, rp, strlen (rp));
pos += strlen (rp);
if (sub >= 0)
break;
}
return 0;
}
int main (int argc, char **argv){
//buf [FILENAME_MAX],
char rp [FILENAME_MAX];
regex_t re;
string toBeReplaced = "-";
string replacedWith = "/";
regcomp (&re, toBeReplaced.c_str(), REG_ICASE);
string buf;
cout << "Enter date separated with dash" << endl;
cin >> buf;
char * replacedWith_ = new char[replacedWith.size() + 1];
std::copy(replacedWith.begin(), replacedWith.end(), replacedWith_);
replacedWith_[replacedWith.size()] = '\0'; // don't forget the terminating 0
char * buf_ = new char[buf.size() + 1];
std::copy(buf.begin(), buf.end(), buf_);
buf_[buf.size()] = '\0'; // don't forget the terminating 0
rreplace (buf_, FILENAME_MAX, &re, strcpy (rp, replacedWith_));
cout<< buf_ << endl;
regfree (&re);
delete[] replacedWith_;
return 0;
}
Ну, этот код работает нормально, если моя строка содержит что-то вроде
22-04-2013
и это изменит его на
22/04/2013
, но я хочу, чтобы это было что-то общее
\d\d-\d\d-\d\d\d\d
подлежит замене на
\d\d/\d\d/\d\d\d\d
как я хочу, чтобы это было общим. Также я работаю в linux g++
, Большинство доступных онлайн-решений находятся на разных платформах. Я также попробовал следующее
string toBeReplaced = "\d[-]\d";
&
string replacedWith = "\d/\d";
но не повезло. и я получаю \d/\d
когда я вхожу 3-4
, Я не знаю почему. Простите, если я спросил что-то глупое.
РЕДАКТИРОВАТЬ
Моя проблема - сопоставить шаблон и заменить его шаблоном. цифру, за которой следует дефис, следует заменить цифрой с косой чертой.
1 ответ
проблема
Вы не можете заменить совпадение большим количеством регулярных выражений, вы получите буквальный текст \d/\d
вместо.
Решение
Для достижения вашей цели вам нужно заменить с помощью группы захвата с обратной ссылкой()
вот так:
(\d{2})-(\d{2})-(\d{4})
Ваша строка замены будет выглядеть следующим образом:
$1/$2/$3
Как вы можете сказать, каждая группа захвата пронумерована. В приведенном выше регулярном выражении есть три группы захвата.
Дополнительные заметки о группах захвата
- Нумерованная группа захвата указывается при каждом переносе выражения в
(regex)
- Чтобы упорядочить выражение, вы можете указать такие группы без захвата, как эта
(?:regex)
- Чтобы упростить обратную ссылку, создайте именованную группу захвата следующим образом:
(?<name>regex)
- Чтобы обратиться к именованной группе захвата в строке замены, используйте
${name}
, Вместо того, чтобы использовать$1
Обратите внимание на приведенные выше примеры, regex
должно быть заменено желаемым регулярным выражением.
Некоторый синтаксис для обратных ссылок может варьироваться в зависимости от различных реализаций Regex, например: \1
вместо $1
демонстрация
Вот демонстрация для визуального представления того, о чем я говорю: