Регулярний вираз, щоб знайти рядок, що міститься між двома символами, в той час як ВИКЛЮЧАЄТЬ роздільники


294

Мені потрібно витягнути з рядка набір символів, які містяться між двома роздільниками, не повертаючи самі роздільники.

Простий приклад повинен бути корисним:

Мета : витягніть підрядок між квадратними дужками, не повертаючи самі дужки.

Базовий рядок :This is a test string [more or less]

Якщо я використовую наступну рег. колишній

\ [. *? \]

Матч є [more or less]. Мені потрібно дістати лише more or less(без дужок).

Чи можна це зробити?


Відповіді:


453

Легко зробити:

(?<=\[)(.*?)(?=\])

З технічної точки зору, це використання макіяжів з оглядовим майданчиком та оглядом. Див . Твердження Lookahead та Lookbehind Zero-Width . Шаблон складається з:

  • передує [не захоплений (дивлячись позаду);
  • не жадібна захоплена група. Зупинятися спочатку не жадно]; і
  • слідує a], що не захоплюється (lookahead).

Крім того, ви можете просто зафіксувати те, що знаходиться між квадратними дужками:

\[(.*?)\]

і повернути першу захоплену групу замість усієї відповідності.


138
"Легко зробити", LOL! :) Регулярні вирази завжди завдають мені головного болю, я прагну забути їх, як тільки знайду ті, що вирішують мої проблеми. Про ваші рішення: перший працює як очікувалося, другий - ні, він продовжує включати дужки. Я використовую C #, можливо, об’єкт RegEx має свій "аромат" двигуна regex ...
Дієго,

5
Це робиться тому, що ви дивитесь на весь матч, а не на першу гру.
клент

Велике спасибі, дуже корисний веб-сайт! Я збережу це як орієнтир. :) Вибачте, якщо я заплутався, розробка C # насправді не одна з моїх навичок ..
Дієго

1
Чи працює це, якщо підрядок також містить роздільники? Наприклад, у This is a test string [more [or] less]цьому поверненні more [or] less?
gnzlbg

1
@gnzlbg ні, воно повернеться "більше [або"
MerickOWA

52

Якщо ви використовуєте JavaScript , перше рішення, яке надає cletus, (?<=\[)(.*?)(?=\])не працюватиме, тому що JavaScript не підтримує оператора "відставання".

Однак друге рішення працює добре, але вам потрібно отримати другий відповідний елемент.

Приклад:

var regex = /\[(.*?)\]/;
var strToMatch = "This is a test string [more or less]";
var matched = regex.exec(strToMatch);

Він повернеться:

["[more or less]", "more or less"]

Отже, те, що вам потрібно, - це друге значення. Використання:

var matched = regex.exec(strToMatch)[1];

Повертати:

"more or less"

2
що робити, якщо в рядку є кілька збігів [більше чи менше]?

Зауваження, що заглядають, були додані до RegExp в ES2018
TheDarkIn1978,

19

Вам просто потрібно «захопити» біт між дужками.

\[(.*?)\]

Щоб захопити, ви помістите його в дужки. Ви не кажете, якою мовою це використовується. Наприклад, в Perl, ви отримаєте доступ до цього за допомогою змінної $ 1.

my $string ='This is the match [more or less]';
$string =~ /\[(.*?)\]/;
print "match:$1\n";

Інші мови матимуть різні механізми. Наприклад, C # використовує клас колекції Match , я вважаю.


Дякую, але це рішення не спрацювало, воно продовжує включати квадратні дужки. Як я писав у коментарі до рішення Клетуса, можливо, об'єкт C # RegEx інтерпретує його по-різному. Я не знаю спеціалістів по C #, тому це лише здогадка, можливо, це лише моя відсутність знань. :)
Дієго

11

[^\[] Відповідайте будь-якому символу, який не є [.

+Зрівняйте 1 або більше всього, що ні [. Створює групи цих збігів.

(?=\])Позитивний lookahead ]. Відповідає групі, що закінчується, ]не включаючи її в результат.

Зроблено.

[^\[]+(?=\])

Доказ.

http://regexr.com/3gobr

Подібно до рішення, запропонованого null. Але додаткові \]не потрібно. В якості додаткової примітки, як видається \, не потрібно уникати [після ^. Для читабельності я б залишив це.

Не працює в ситуації, коли роздільники однакові. "more or less"наприклад.


8

PHP:

$string ='This is the match [more or less]';
preg_match('#\[(.*)\]#', $string, $match);
var_dump($match[1]);


3

У мене була така ж проблема, коли я використовував регекс з сценарієм bash. Я використовував двоетапний розчин, використовуючи труби з нанесенням grep -o

 '\[(.*?)\]'  

спочатку, потім

'\b.*\b'

Очевидно, не настільки ефективні в інших відповідях, але альтернативні.


3

Цей спеціально працює для аналізатора регулярного вираження JavaScript /[^[\]]+(?=])/g

просто запустіть це в консолі

var regex = /[^[\]]+(?=])/g;
var str = "This is a test string [more or less]";
var match = regex.exec(str);
match;

2

Я хотів знайти рядок між / і #, але # іноді необов’язково. Ось регекс, який я використовую:

  (?<=\/)([^#]+)(?=#*)

0

Ось як я потрапив без '[' і ']' в C #:

        var text = "This is a test string [more or less]";
        //Getting only string between '[' and ']'
        Regex regex = new Regex(@"\[(.+?)\]");
        var matchGroups = regex.Matches(text);
        for (int i = 0; i < matchGroups.Count; i++)
        {
            Console.WriteLine(matchGroups[i].Groups[1]);
        }

Вихід:

more or less

-1

Якщо вам потрібно витягнути текст без дужок, ви можете використовувати bash awk

echo " [hola mundo] " | awk -F'[][]' '{print $2}'

результат:

hola mundo

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