Regex для удаления неповторяющихся пробелов

Я получаю информацию об имени из PDF-файла в Python с помощью fitz.

Проблема в том, что большая часть информации имеет пробелы, соответствующие фону, что дает мне, например: имя = «P I E R R E» и фамилия «L E D U C D E C O L».

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

Конечно, сначала я удалил все пробелы с «s/\s//g», но в качестве имени мне дали «LEDUCDECOL», а мне нужно «LE DUC DE COL».

как я могу знать, что это должно быть «LE DUC DE COL», а не «LEDUCDECOL», «LEDU DECOL», «LEDU CDE COL» и т. д.? У вас не может быть регулярного выражения для этого, поскольку у вас, очевидно, есть больше правил, которые регулярное выражение не может выполнить.

Marcin Orlowski 07.10.2023 14:29

теперь я думаю, что получил то, что ты хотел. чтобы разделить LE DUC DE, используйте v = re.sub(r'(LE|DUC|DE)', r"\1 ", v)

LetzerWille 07.10.2023 15:38

Попробуйте использовать re.sub(' ( ?)', r'\1', s) (также см. эту демонстрацию regex101 ). Он соответствует пробелу и захватывает необязательный пробел в первую группу. Затем захват вставляется в замену (если после пробела был пробел).

bobble bubble 07.10.2023 21:11
Почему в Python есть оператор "pass"?
Почему в Python есть оператор "pass"?
Оператор pass в Python - это простая концепция, которую могут быстро освоить даже новички без опыта программирования.
Некоторые методы, о которых вы не знали, что они существуют в Python
Некоторые методы, о которых вы не знали, что они существуют в Python
Python - самый известный и самый простой в изучении язык в наши дни. Имея широкий спектр применения в области машинного обучения, Data Science,...
Основы Python Часть I
Основы Python Часть I
Вы когда-нибудь задумывались, почему в программах на Python вы видите приведенный ниже код?
LeetCode - 1579. Удаление максимального числа ребер для сохранения полной проходимости графа
LeetCode - 1579. Удаление максимального числа ребер для сохранения полной проходимости графа
Алиса и Боб имеют неориентированный граф из n узлов и трех типов ребер:
Оптимизация кода с помощью тернарного оператора Python
Оптимизация кода с помощью тернарного оператора Python
И последнее, что мы хотели бы показать вам, прежде чем двигаться дальше, это
Советы по эффективной веб-разработке с помощью Python
Советы по эффективной веб-разработке с помощью Python
Как веб-разработчик, Python может стать мощным инструментом для создания эффективных и масштабируемых веб-приложений.
0
3
93
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

# doing it with no loop, just regex

firstname = "P I E R R E"
lastname = "L E  D U C  D E  C O L"

re.sub(r' ', '', firstname) + " " + " ".join([x.replace(" ", "") for x in re.split(r'\s{2}', lastname)])
'PIERRE LE DUC DE COL'

@LetzterWille Я отредактировал вопрос ouzmoutous. Поскольку строка не была отформатирована, двойные пробелы в строке примера L E D U C D E C O L не были видны.

bobble bubble 07.10.2023 21:15

@bobblebubble. Спасибо. Думаю, многих это смутило.

LetzerWille 07.10.2023 22:54
Ответ принят как подходящий

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

При замене используйте значение группы 1, используя \1

 ( )*

Если вы хотите сопоставить пробельный символ, вы можете заменить его на \s, но учтите, что он также может соответствовать новой строке:

\s(\s)*

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

Например:

import re
 
strings = [
    "L E  D U C  D E  C O L",
    "a        b     c def g"
]
pattern = r" ( )*"
for s in strings:
    print(re.sub(pattern, r"\1", s))

Выход

LE DUC DE COL
a b cdefg

Если вы хотите сопоставить один пробел, за которым не следует другой пробел, вы можете использовать отрицательный просмотр вперед и использовать пустую строку в замене:

 (?! )

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

Отличный полный ответ, спасибо!

ouzmoutous 12.10.2023 10:23

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