2013-08-22 1 views
9

Возможно ли это: получить (аналогично) функциональность Stanford Named Entity Recognizer, используя только NLTK?Функциональность распознавателя Entity Recognizer (NER) Stanford с NLTK

Есть ли какой-нибудь пример?

В частности, меня интересует извлечение LOCATION часть текста. Например, из текста

Встреча будет проходить в 22 West Westin ул., Южная Каролина, 12345 на ноябрь-18

в идеале я хотел бы получить что-то вроде

(S 
22/LOCATION 
(LOCATION West/LOCATION Westin/LOCATION) 
st./LOCATION 
,/, 
(South/LOCATION Carolina/LOCATION) 
,/, 
12345/LOCATION 

.....

или просто

22 West Westin st., South Carolina, 12345 

Вместо этого, я только в состоянии получить

(S 
    The/DT 
    meeting/NN 
    will/MD 
    be/VB 
    held/VBN 
    at/IN 
    22/CD 
    (LOCATION West/NNP Westin/NNP) 
    st./NNP 
    ,/, 
    (GPE South/NNP Carolina/NNP) 
    ,/, 
    12345/CD 
    on/IN 
    Nov.-18/-NONE-) 

Обратите внимание, что если я ввожу свой текст в http://nlp.stanford.edu:8080/ner/process я получаю результаты далеки от совершенства (номер улицы и почтовый индекс по-прежнему не хватает), но по крайней мере, «ул. " является частью LOCATION, а Южная Каролина - РАСПОЛОЖЕНИЕ, а не «GPE/NNP»:?

Что я делаю неправильно, пожалуйста? как я могу исправить это, чтобы использовать NLTK для извлечения фрагмента места из некоторого текста?

Большое спасибо заранее!

ответ

19

nltk У ДЕЯТЕЛЬНОСТИ есть интерфейс для Stanford NER, check nltk.tag.stanford.NERTagger.

from nltk.tag.stanford import NERTagger 
st = NERTagger('/usr/share/stanford-ner/classifiers/all.3class.distsim.crf.ser.gz', 
       '/usr/share/stanford-ner/stanford-ner.jar') 
st.tag('Rami Eid is studying at Stony Brook University in NY'.split()) 

выход:

[('Rami', 'PERSON'), ('Eid', 'PERSON'), ('is', 'O'), ('studying', 'O'), 
('at', 'O'), ('Stony', 'ORGANIZATION'), ('Brook', 'ORGANIZATION'), 
('University', 'ORGANIZATION'), ('in', 'O'), ('NY', 'LOCATION')] 

Однако каждый раз, когда вы звоните tag, NLTK просто пишет целевое предложение в файл и запускает инструмент командной строки Stanford ЕЙ разобрать этот файл и, наконец, разбирает вывод обратно питон. Поэтому накладные расходы на классификаторы загрузки (около 1 минуты для меня каждый раз) неизбежны.

Если это проблема, используйте Pyner.

Первый запуск Stanford НЭК в качестве сервера

java -mx1000m -cp stanford-ner.jar edu.stanford.nlp.ie.NERServer \ 
-loadClassifier classifiers/english.all.3class.distsim.crf.ser.gz -port 9191 

затем перейдите в папку pyner

import ner 
tagger = ner.SocketNER(host='localhost', port=9191) 
tagger.get_entities("University of California is located in California, United States") 
# {'LOCATION': ['California', 'United States'], 
# 'ORGANIZATION': ['University of California']} 
tagger.json_entities("Alice went to the Museum of Natural History.") 
#'{"ORGANIZATION": ["Museum of Natural History"], "PERSON": ["Alice"]}' 

Надежда это помогает.

+1

Знаете ли вы, смогу ли я обучить Стэнфордского НЭР и как? Я попробовал. «Волшебник из страны Оз покидает Изумрудный город». и «Александр Великий покорил Империю Персии». Ничего не сработало. – Hans

+0

@edfward java запускает его на порт 9191, но python запускает его на порт 8080. Почему? – bernie2436

+0

@ akh2103 моя ошибка. Я исправился в ответ, они должны быть согласованы, в то время как фактический порт может меняться. – junjiah