Что касается части регулярных выражений, ваши паттерны "немного отклонены". Чаще всего вы пропускаете понятие класса символов , [abc]
, как шаблоны, которые соответствуют одному символу из набора, определенного в классе.
Регулярное выражение для обнаружения слов с апострофами и через дефис:
pat=re.compile(r"(?:\w+['’])?\w+(?:-(?:\w+['’])?\w+)*")
См. Демоверсию regex . Однако он также будет соответствовать обычным числам или простым словам. Чтобы избежать их соответствия, вы можете использовать
pat=re.compile(r"(?:\w+['’])?\w+(?:-(?:\w+['’])?\w+)+|\w+['’]\w+")
См. это демо регулярных выражений .
Детали
(?:\w+['’])?
- необязательная группа без захвата, соответствующая 1 или 0 вхождениям из 1+ слов с последующими либо '
, либо ’
\w+
- 1 или более символов слова
(?:-(?:\w+['’])?\w+)*
- 0 или более повторений
-(?:\w+['’])?
- необязательная группа без захвата, соответствующая 1 или 0 вхождениям из 1+ слов с последующими либо '
, либо ’
\w+
- 1 или более слов с символами
Далее reg = list(filter(pat.match, freq))
может не выполнять то, что вам нужно, поскольку re.match
соответствует только началу строки . Скорее всего, вы хотите использовать re.match
:
reg = list(filter(pat.search, freq))
^^^^^^
Регулярное выражение для слов, начинающихся с заглавной буквы, может быть написано как
patt=re.compile(r"\b[A-Z][a-z]*\b")
c_n= list(filter(patt.search, freq))
См. это демо регулярных выражений
\b
соответствует границе слова, [A-Z]
соответствует любой прописной букве ASCII, часть [a-z]*
соответствует 0 или более строчным буквам ASCII, а \b
обеспечивает наличие границы слова после них.