У меня есть файл, формат которого я изменяю с помощью скрипта Python. В этом файле у меня есть несколько строк в верблюжьей оболочке, в которые я просто хочу вставить один пробел перед заглавной буквой - поэтому «WordWordWord» становится «Word Word Word», но у меня также есть некоторые сокращения, как в тексте «Генеральный менеджер или VP » .
Я нашел ответ от Дэвида Андерхилла в этом посте:
Питонический способ вставить пробел перед заглавными буквами
Хотя этот ответ помогает мне не вставлять пробелы между аббревиатурами в тексте, например "DaveIsAFKRightNow! Cool"
Но он обязательно вставляет пробел между V и P в «VP».
У меня только 25 очков опыта, и я не могу комментировать существующее сообщение, у меня нет другого выбора, кроме как создать еще одно сообщение для решения подобной проблемы.
Я не так хорош в RegEx и не могу понять, как справиться с этой ситуацией.
Я пробовал это:
re_outer = re.compile(r'([^A-Z ])([A-Z])')
re_inner = re.compile(r'(?<!^)([A-Z])([^A-Z])')
re_outer.sub(r'\1 \2', re_inner.sub(r' \1\2', 'DaveIsAFKRightNow!Cool'))
Это дает мне «Дейв АФК прямо сейчас! Прохладно'
Мой текстовый пример такой:
General Manager or VP Torrance, CARequired education
Я хочу вывод как: General Manager or VP Torrance, CA Required education
Вывод, который я получаю: General Manager or V P Torrance, CA Required education
2 ответа
Вы можете поменять местами замены, чтобы сначала вставить пробелы перед заглавными буквами, которым предшествуют символы, отличные от заглавных букв и пробелов, а затем добавить пробел перед словами, начинающимися с 1+ заглавными буквами, за которыми следуют прописные и строчные буквы:
import re
re_outer = re.compile(r'([^A-Z ])([A-Z])')
re_inner = re.compile(r'\b[A-Z]+(?=[A-Z][a-z])')
print(re_inner.sub(r'\g<0> ', re_outer.sub(r'\1 \2', 'DaveIsAFKRightNow!Cool')))
# => Dave Is AFK Right Now! Cool
print(re_inner.sub(r'\g<0> ', re_outer.sub(r'\1 \2', 'General Manager or VP Torrance, CARequired education')))
# => General Manager or VP Torrance, CA Required education
\b[A-Z]+(?=[A-Z][a-z])
регулярное выражение соответствует
\b
- граница слова[A-Z]+
- 1+ заглавные буквы, которые(?=[A-Z][a-z])
- сопровождается заглавной буквой и строчной буквой.
Обратите внимание, что \g<0>
вставляет все совпадения в шаблон замены.
В качестве альтернативы вы можете использовать один шаблон с чередованием:
((?<=[^\W[A-Z])[A-Z]|(?<=\S)[A-Z](?=[a-z]))
В замене используйте пробел, за которым следует группа 1:
\1
Объяснение
(
Группа захвата < UL>-
(?<=
Позитивный взгляд, утверждаю, что справа < UL> -
[^\W[A-Z]
Соответствует символу слова, кроме A-Z
)
Закрыть позитивный взгляд |
или (?<=\S)
Позитивный взгляд сзади, утверждают, что слева находится [A-Z]
Соответствует A-Z (?=[a-z])
Позитивный взгляд, утверждаем, что справа - a-z )
Закрыть группу захватаRegex demo | демонстрация Python
Например
import re
strings = [
"General Manager or VP Torrance, CARequired education",
"WordWordWord",
"DaveIsAFKRightNow!Cool"
]
pattern = re.compile(r'((?<=[^\W[A-Z])[A-Z]|(?<=\S)[A-Z](?=[a-z]))')
for str in strings:
print(pattern.sub(r' \1', str))
Результат
General Manager or VP Torrance, CA Required education
Word Word Word
Dave Is AFK Right Now! Cool
Похожие вопросы
Связанные вопросы
Новые вопросы
regex
Регулярные выражения предоставляют декларативный язык для сопоставления шаблонов в строках. Они обычно используются для проверки, синтаксического анализа и преобразования строк. Поскольку регулярные выражения не полностью стандартизированы, все вопросы с этим тегом должны также включать тег, определяющий применимый язык программирования или инструмент.