Регулярное выражение

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

location in [chambre, cuisine, salle-de-bain, jardin]

Всего за один шаг я хочу убедиться, что фигура представляет собой слово в [слово, слово, слово...], и я хотел бы поймать каждое слово. (Я хочу сделать это только в один шаг для производительности, потому что этот код уже работает с тремя шагами, но это слишком долго)

Мое текущее регулярное выражение:

/([a-zA-Z]+)\s+in\s+\[\s*([a-zA-Z-]+)\s*(?:,\s*([a-zA-Z-]+)\s*)*\s*\]/

Я ловлю локацию, chambre и jardin. Я не ловлю кухню и саль-де-бен

$condition = 'location in [chambre, cuisine, salle-de-bain, jardin]'
$analyse = preg_match('/([a-zA-Z]+)\s+in\s+\[\s*([a-zA-Z-]+)\s*(?:,\s*([a-zA-Z-]+)\s*)*\s*\]/',$condition, $matches);
var_dump($matches);
array:4 [▼
  0 => "location in [chambre, cuisine, salle-de-bain, jardin]"
  1 => "location"
  2 => "chambre"
  3 => "jardin"
]

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

В PHP повторяющиеся группы захвата всегда будут сохранять только последнюю захваченную подстроку.

Wiktor Stribiżew 09.05.2022 12:12
Стоит ли изучать PHP в 2026-2027 годах?
Стоит ли изучать PHP в 2026-2027 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Symfony Station Communiqué - 7 июля 2023 г
Symfony Station Communiqué - 7 июля 2023 г
Это коммюнике первоначально появилось на Symfony Station .
Оживление вашего приложения Laravel: Понимание режима обслуживания
Оживление вашего приложения Laravel: Понимание режима обслуживания
Здравствуйте, разработчики! В сегодняшней статье мы рассмотрим важный аспект управления приложениями, который часто упускается из виду в суете...
Установка и настройка Nginx и PHP на Ubuntu-сервере
Установка и настройка Nginx и PHP на Ubuntu-сервере
В этот раз я сделаю руководство по установке и настройке nginx и php на Ubuntu OS.
Коллекции в Laravel более простым способом
Коллекции в Laravel более простым способом
Привет, читатели, сегодня мы узнаем о коллекциях. В Laravel коллекции - это способ манипулировать массивами и играть с массивами данных. Благодаря...
Как установить PHP на Mac
Как установить PHP на Mac
PHP - это популярный язык программирования, который используется для разработки веб-приложений. Если вы используете Mac и хотите разрабатывать...
2
1
40
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

В PHP повторяющиеся группы захвата всегда будут сохранять только последнюю захваченную подстроку.

Вы можете использовать preg_match_all с регулярным выражением, например

[a-zA-Z]+(?=\s+in\s+\[\s*[a-zA-Z-]+(?:\s*,\s*[a-zA-Z-]+)*\s*])|(?:\G(?!^)\s*,\s*|(?<=[a-zA-Z])\s+in\s+\[\s*)\K[a-zA-Z-]+(?=(?:\s*,\s*[a-zA-Z-]+)*\s*])

См. демонстрация регулярных выражений. Подробности:

  • [a-zA-Z]+(?=\s+in\s+\[\s*[a-zA-Z-]+(?:\s*,\s*[a-zA-Z-]+)*\s*]) - одна или несколько букв ASCII, за которыми сразу следует in, заключенная в один или несколько пробельных символов, затем [, ноль или более пробелов, одна или несколько букв ASCII или дефис, затем ноль или более повторений запятой, заключенная в ноль или более пробелы, а затем одна или несколько букв или дефисов ASCII, затем ноль или более пробелов и символ ]
  • | - или
  • (?:\G(?!^)\s*,\s*|(?<=[a-zA-Z])\s+in\s+\[\s*)\K[a-zA-Z-]+(?=(?:\s*,\s*[a-zA-Z-]+)*\s*]):
    • (?:\G(?!^)\s*,\s*|(?<=[a-zA-Z])\s+in\s+\[\s*) - конец предыдущего совпадения и запятая, заключенная с нулем или более пробелами, или место, которому непосредственно предшествует буква ASCII, затем один или несколько пробелов, in, один или несколько пробелов, [ и ноль или более пробелов
    • \K - пропустить совпадающий текст
    • [a-zA-Z-]+ - одна или несколько букв ASCII или дефисов
    • (?=(?:\s*,\s*[a-zA-Z-]+)*\s*]) - положительный просмотр вперед, который требует ноль или более повторений запятой, заключенной в ноль или более пробелов, а затем одну или несколько букв или дефисов ASCII, затем ноль или более пробелов и символ ].

Большое спасибо за ваш полный ответ. Я ценю его!

Alexandre Tranchant 09.05.2022 14:01

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