Ответ 1
Сверху моей головы вы можете попробовать:
\b # word boundary - matches start of word
(?!girl) # negative lookahead for literal 'girl'
\w* # zero or more letters, numbers, or underscores
friend # literal 'friend'
\b # word boundary - matches end of word
Обновление
Вот еще один неочевидный подход, который должен работать в любой современной реализации регулярных выражений:
Предполагая, что вы хотите извлечь шаблон, который появляется в нескольких контекстах, но вы хотите только сопоставить, если он отображается в определенном контексте, вы можете использовать изменение, в котором вы сначала указываете, чего не хотите, а затем фиксируете, что вы делаете.
Итак, используя ваш пример, чтобы извлечь все слова, которые либо находятся, либо заканчиваются в friend
кроме girlfriend
, вы должны использовать:
\b # word boundary
(?: # start of non-capture group
girlfriend # literal (note 1)
| # alternation
( # start of capture group #1 (note 2)
\w* # zero or more word chars [a-zA-Z_]
friend # literal
) # end of capture group #1
) # end of non-capture group
\b
Примечания:
- Это то, что мы не делаем, чтобы захватить.
- И это то, что мы делаем, чтобы захватить.
Что можно охарактеризовать как:
- для всех слов
- во-первых, сопоставить "подругу" и не захватывать (отбрасывать)
- затем сопоставить любое слово, которое заканчивается "другом" или заканчивается, и захватывать его
В Javascript:
const target = 'A boyfriend and girlfriend gained a friend when they asked to befriend them';
const pattern = /\b(?:girlfriend|(\w*friend))\b/g;
let result = [];
let arr;
while((arr=pattern.exec(target)) !== null){
if(arr[1]) {
result.push(arr[1]);
}
}
console.log(result);
который при запуске будет печатать:
[ 'boyfriend', 'friend', 'befriend' ]