Як зіставити цілий рядок із регулярним виразом?


82

Мені потрібен регулярний вираз, який буде знаходити лише ті збіги, де весь рядок відповідає моєму запиту.

Наприклад, якщо я шукаю фільми з назвою "Червоний Жовтень", я хочу лише відповідати саме тому заголовку (не враховуючи регістр), але не збігатись із заголовками, як "Полювання на Червоний Жовтень". Не зовсім впевнений, що знаю, як це зробити. Хтось знає?

Дякую!


1
Навіщо вам регулярний вираз для чогось, на що простий string.Containsбуде працювати?
— Оді

1
Причина, по якій мені потрібно використовувати регулярний вираз, полягає в тому, що я використовую його для пошуку в MongoDB, і мені потрібно, щоб він не враховував регістр, що можна зробити лише за допомогою регулярного виразу
— Micah

Чому б не перетворити (на льоту) дані db у малі та користувацькі рядки нижнього регістру для пошуку?
— greenoldman

1
@macias Я не погоджуюся з тим, що це був би кращий варіант, але, на жаль, моя нинішня ситуація цього не дозволяє.
— Михей

FYI, якщо не вимагає використання регулярних виразів, просто намагаюся порівняти два рядки без урахування регістру, можна просто зробитиstring1.Equals(string2, StringComparison.OrdinalIgnoreCase);
— ToolmakerSteve

Відповіді:


111

Спробуйте наступний регулярний вираз:

^Red October$

За замовчуванням регулярні вирази чутливі до регістру. У ^Зазначає початок тексту відповідності і $кінця.


1
FYI, варто згадати, що, щоб зробити його чутливим до регістру, при створенні об’єкта регулярного виразу додайте другий параметр RegexOptions.IgnoreCase
— ToolmakerSteve

Це не працює, якщо щось інше оточує цей рядок. Наприклад, якщо ви шукали "St", як у Street, але у вас є інші рядки в тому ж рядку, які також починаються на "St", такі як ім'я "Stirling", цей регулярний вираз не буде точно відповідати. Я не впевнений, що RegEx - правильна відповідь для цього сценарію, на жаль. Я збираюся продовжувати намагатися, хоча. Відповідь Тіма нижче хороша, але не всі двигуни це підтримують.
— dislexicanaboko

Насправді, $це не завжди відповідає кінці рядка, \zце робить ( \Zце еквівалент у Python). Дивіться відповідь Тіма Піцкера . Це правда для JavaScript.
— Wiktor Stribiżew

42

Як правило, і за замовчуванням, ^і $прив’язки - це хороший спосіб забезпечити відповідність регулярного виразу цілому рядку.

Однак кілька застережень:

Якщо у вас є чергування в своєму регулярному виразі, обов'язково укладіть регулярний вираз в не захоплюючи групи , перш ніж навколишній ^і $:

^foo|bar$

звичайно відрізняється від

^(?:foo|bar)$

Крім того, ^і $може набувати іншого значення (початок / кінець рядка замість початку / кінця рядка ), якщо встановлено певні параметри. У текстових редакторах, які підтримують регулярні вирази, зазвичай це поведінка за замовчуванням. У деяких мовах, особливо Ruby, таку поведінку навіть не можна вимкнути.

Тому існує інший набір прив’язок, які гарантовано збігатимуться лише на початку / в кінці цілого рядка:

\A збіги на початку рядка.

\Z збіги в кінці рядка або перед остаточним розривом рядка.

\z збіги в самому кінці рядка.

Але не всі мови підтримують ці прив'язки, особливо JavaScript.


4
це найбільш корисна відповідь
— Jeremy Danyow

18

Використовуйте модифікатори ^та $для позначення місця розташування шаблону регулярного виразу відносно початку та кінця рядка:

Regex.Match("Red October", "^Red October$"); // pass
Regex.Match("The Hunt for Red October", "^Red October$"); // fail

10

Я знаю, що це може запізнитися, щоб відповісти на це, але, можливо, це стане в нагоді комусь іншому.

Найпростіший спосіб:

var someString = "...";
var someRegex = "...";
var match = Regex.Match(someString , someRegex );
if(match.Success && match.Value.Length == someString.Length){
    //pass
} else {
    //fail
}

2
ІМХО це МЕНШ простіше, ніж прийнята відповідь. Але це альтернатива.
— ToolmakerSteve

Мені подобається ця відповідь, оскільки сам код показує передбачувану поведінку, а не модифікує регулярний вираз (що може бути менш зрозумілим для тих, хто кидає погляд на код із незначним розумінням регулярного виразу). Потенційна гикавка полягає в тому, що регулярний вираз можна записати так, щоб він міг відповідати цілому рядку або його частині, а функція Regex.Match повертає частковий збіг, хоча можливе повне збіг.
— Джон Тойтс,

8

Вам потрібно вкласти свій регулярний вираз у ^(початок рядка) та $(кінець рядка):

^Red October$

0

Вибачте, але це трохи незрозуміло.

З того, що я прочитав, ви хочете зробити просте порівняння рядків. Для цього вам не потрібно регулярний вираз.

string myTest = "Red October";
bool isMatch = (myTest.ToLower() == "Red October".ToLower());
Console.WriteLine(isMatch);
isMatch = (myTest.ToLower() == "The Hunt for Red October".ToLower());

1
Причиною того, що мені потрібно використовувати регулярний вираз, є те, що я використовую його для пошуку в MongoDB, і мені це потрібно, щоб не враховувати регістр, що можна зробити лише за допомогою регулярного виразу.
— Micah

-1

Ви можете зробити це як цей приклад, якщо я хочу лише один раз вловити літеру мінус a у рядку, і це можна перевірити за допомогою myRegex.IsMatch ()

^ [^ e] [e] {1} [^ e] $

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.