Как я могу хранить имена из нескольких слов в токенизации вместе? - PullRequest
1 голос
/ 09 октября 2019

Я хочу классифицировать документы, используя функции TF-IDF. Один из способов сделать это:

from sklearn.feature_extraction.text import TfidfVectorizer
import string
import re
import nltk


def tokenize(document):
    document = document.lower()
    for punct_char in string.punctuation:
        document = document.replace(punct_char, " ")
    document = re.sub('\s+', ' ', document).strip()

    tokens = document.split(" ")

    # Contains more than I want:
    # from spacy.lang.de.stop_words import STOP_WORDS
    stopwords = nltk.corpus.stopwords.words('german')
    tokens = [token for token in tokens if token not in stopwords]
    return tokens

# How I intend to use it
transformer = TfidfVectorizer(tokenizer=tokenize)

example = "Jochen Schweizer ist eines der interessantesten Unternehmen der Welt, hat den Sitz allerdings nicht in der Schweizerischen Eidgenossenschaft."
transformer.fit([example])

# Example of the tokenizer
print(tokenize(example))

Один недостаток этого токенизатора состоит в том, что он разделяет слова, которые принадлежат друг другу: «Йохен Швейцер» и «schweizerische Eidgenossenschaft». Также отсутствует лемматизация (слово stemming). Я хотел бы получить следующие токены:

["Jochen Schweizer", "interessantesten", "unternehmen", "Welt", "Sitz", "allerdings", "nicht", "Schweizerische Eidgenossenschaft"]

Я знаю, что Spacy может идентифицировать эти именованные объекты (NER):

import en_core_web_sm  # python -m spacy download en_core_web_sm --user
parser = en_core_web_sm.load()
doc = parser(example)
print(doc.ents)  # (Jochen Schweizer, Welt, Sitz)

Есть ли хороший способ использовать spacy для токенизациитаким образом, что слова именованных сущностей остаются вместе?

1 Ответ

2 голосов
/ 09 октября 2019

Как насчет этого:

with doc.retokenize() as retokenizer:
    for ent in doc.ents:
        retokenizer.merge(doc[ent.start:ent.end])

Фактически, вы можете использовать spacy для удаления знаков препинания и стоп-слов, а также выполнять лемматизацию!

parser = spacy.load('de_core_news_sm')
def tokenize(text):
    doc = parser(text)
    with doc.retokenize() as retokenizer:
        for ent in doc.ents:
            retokenizer.merge(doc[ent.start:ent.end], attrs={"LEMMA": ent.text})
    return [x.lemma_ for x in doc if not x.is_punct and not x.is_stop]

Пример:

>>> text = "Jochen Schweizer ist eines der interessantesten Unternehmen der Welt, hat den Sitz allerdings nicht in der Schweizerischen Eidgenossenschaft."
>>> print(tokenize(text))
>>> [u'Jochen Schweizer', u'interessant', u'Unternehmen', u'Welt', u'Sitz', u'Schweizerischen Eidgenossenschaft']
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...