QRegularExpression: пропустить соответствующие экранированные токены

Я заменяю QString с помощью QRegularExpression но у меня проблема с сбежавшими токенами.

Например: "{aaa}" в строке следует заменить на "bbb" но "\{aaa}" следует игнорировать и "{aaa}" будет установлен (без "\").

например:

это тест с именем {aaa} -> это тест с именем bbb
это тест с именем \{aaa} -> это тест с именем {aaa}

я использую

QString& replace(const QRegularExpression& re, const QString& after);

но я не могу найти способ пропустить сбежавший матч. Я думаю, с negative look-behind, но как?

2 ответа

Решение

Шаблон, который вы придумали - (?<!\\){aaa} - не будет соответствовать действительному {aaa} которому предшествует действительный экранированный обратный слеш, \\{aaa}Посмотрите это демо.

То, что вам нужно, это регулярное выражение, которое будет учитывать эти экранированные обратные косые черты:

(?<!\\)(?:\\{2})*\K{aaa}

Смотрите демо-версию регулярного выражения.

Детали:

  • (?<!\\) - отрицательный взгляд за неудачей матча, если есть \ непосредственно слева от текущего местоположения
  • (?:\\{2})* - ноль или более случаев появления двойной обратной косой черты
  • \K - оператор сброса совпадений, отбрасывающий найденный текст
  • {aaa} - буквальный {aaa} подстрока.

В Qt строковые литералы могут содержать escape-последовательности, \n для новой строки, \r для возврата каретки и т. д. Чтобы определить буквенную обратную косую черту (которая используется для формирования escape- выражений регулярных выражений, операторов регулярных выражений, сокращенных классов символов), необходимо удвоить обратную косую черту:

QRegularExpression re("(?<!\\\\)(?:\\\\{2})*\\K{aaa}")

Я нашел решение:

QRegularExpression re(QString("(?<!\\\\)({aaa})")

Я просто пропустил, чтобы соответствовать обратной косой черте, 4 должны быть использованы.

Другие вопросы по тегам