Поиск конкретного символа в строке в кавычках - PullRequest
1 голос
/ 08 сентября 2011

Я новичок в регулярных выражениях, но скоро планирую освоить его. Сейчас мне нужна ваша помощь для выполнения следующих действий:

Я хочу найти все запятые (,), которые находятся между литеральными / цитируемыми (") строками.

Например:

"bla bla , bla bla"

, а также:

","

но не если это разделитель аргументов, например:

Replace("abc","b","f")

Может быть, это очень просто, если вы знаете регулярное выражение, но для меня нет (пока);).

1 Ответ

1 голос
/ 08 сентября 2011

Вы начинаете с чего-то подобного

"[^"]*"

Это самый простой способ сопоставить то, что указано. Затем вы измените его в соответствии с вашим шаблоном запятой.

"[^",]*,[^"]*"

Но вы не хотите захватывать запятую, чтобы создать группу

"[^",]*(,)[^"]*"

И затем, чтобы иметь возможность найти много запятых в одной строке, вы можете использовать повтор с группой без захвата.

"(?:[^",]*(,))+[^"]*"

Это должно работать для вас, регулярные выражения несколько ограничены и лучше всего работают при правильном использовании. Приведенный выше шаблон ищет квоту, ищет вещи, которые не являются кавычками, а затем продолжает поиск. Он основан на повторении первой группы, так что он может найти запятые в строке (вы получите доступ к ним в свойстве Captures этой группы, когда сделаете совпадение).

var regex = new Regex("\"(?:[^\",]*(,))+[^\"]*\"");
var m = regex.Match("a,b,c");
m.Groups[1].Captures // <-- all commas are captured in this collection

Пока строка сама по себе не содержит кавычек, это будет хорошо работать, но трудно принять escape-последовательности внутри строк в кавычках с регулярным выражением. Это то, с чем они плохо справляются. Так что, пока это хорошо, иди с ним.

Теперь к вопросу о ситуации, когда у вас есть этот тип строки "a","b". Сканирование строки с использованием регулярного выражения будет совпадать слева направо и потреблять символы в таком порядке, если любое совпадение будет успешным, оно не сможет продолжить сопоставление другим способом. Проблема здесь в том, что строка в кавычках без кавычек не является успешным совпадением (если мы сделаем это совпадением, но проигнорируем его, мы можем обойти это).

Мы всегда сначала пытаемся произвести первоначальное деривацию, но возвращаемся к простой строке в кавычках, которую мы просто игнорируем, таким образом, она пропускает голову и не считает середину строки допустимым совпадением. Все дело в том, чтобы конечный автомат, то есть регулярное выражение, мог следить за открытием и закрытием указанных значений.

"(?:[^",]*(,))+[^"]*"|"[^"]*"

Это ваше окончательное решение, но вы должны проверить, что Group[1] успешно, потому что теперь шаблон успешен, если он находит строку в кавычках, а группа захвата Group[1] - нет.

var regex = new Regex("\"(?:[^\",]*(,))+[^\"]*\"|\"[^\"]*\"");
var m = regex.Match("a,b,c");
if (m.Groups[1].Success)
{
    // Do your thing ;)
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...