4719
Вивчення методів доступу та роботи з лексичним ресурсами на мові Python
Лабораторная работа
Информатика, кибернетика и программирование
Вивчення основ програмування на мові Python. Вивчення методів доступу та роботи з лексичним ресурсами. Семантичний словник англійської мови WordNet. Короткі теоретичні відомості Поняття функції та модуля. При програм...
Украинкский
2012-11-25
646.5 KB
5 чел.
При програмуванні часто необхідно частину програми виконати (використати) декілька разів. Наприклад, потрібно написати програму, яка здійснює утворення множини з однини іменників і вона буде виконуватись в різних місцях програми. Швидше ніж повторювати той самий код декілька разів і більш ефективно і надійно організувати цю роботу через функцію. Функція - це програмна конструкція, яку можна викликати з одним або більше вхідними параметрами, і отримувати результат на виході. Визначаємо функцію, використовуючи ключове слово def далі потрібно дати назву функції і визначити вхідні параметри, після двокрапки записується тіло функції. Ключове слово return використовується для відображення значення, яке ми хочемо отримати на виході функції. Розглянемо приклад. Функція plural () отримує на вході однину іменника і формує множину на виході.
def plural(word):
if word.endswith('y'):
return word[:-1] + 'ies'
elif word[-1] in 'sx' or word[-2:] in ['sh', 'ch']:
return word + 'es'
elif word.endswith('an'):
return word[:-2] + 'en'
else:
return word + 's'
>>> plural('fairy')
'fairies'
>>> plural('woman')
'women'
Розробляючи ту чи іншу програму протягом довшого періоду додаючи до неї нові функції і змінюючи існуючі або розробляючи декілька версій однієї програми потрібно зберігати тексти програм в окремих файлах і організовувати доступ до відповідних функцій в цих програмах. Збережемо текст останньої функції plural () в окремому файлі textproc.py. тепер можна доступитися до цієї функції імпортувавши її з файлу.
>>> from textproc import plural
>>> plural('wish')
wishes
>>> plural('fan')
fen
Множина змінних і функцій збережених у файлі називаються в Python модулем. Множина повязаних між собою модулів називають пакетом. Програма обробки корпуса Brown це є приклад модуля, а множина програм для роботи зі всіма корпусами це є приклад пакету. NLTK це множина пакетів, яку називають бібліотекою.
Умовний частотний розподіл можна використати для побудови таблиці біграмів (пар слів). Функція NLTK bigrams() , як аргумент бере список слів і повертає список послідовних пар слів.
>>> sent = ['In', 'the', 'beginning', 'God', 'created', 'the', 'heaven',
... 'and', 'the', 'earth', '.']
>>> nltk.bigrams(sent)
[('In', 'the'), ('the', 'beginning'), ('beginning', 'God'), ('God', 'created'),
('created', 'the'), ('the', 'heaven'), ('heaven', 'and'), ('and', 'the'),
('the', 'earth'), ('earth', '.')]
В наступному прикладі кожне слово розглядається, як умова і для кожного з них будується частотний розподіл по словам, які слідують після нього. Функція generate_model() містить простий цикл для генерації тексту. Коли ця функція викликається то одним з її аргументів є слово початковий контекст (у прикладі 'living') .
В циклі поточне значення змінної word виводиться на екран і її значення замінюється на слово, яке найчастіше є наступним словом (max()) . На наступному кроці циклу вже це слово буде наступним контекстом. Запропонований підхід генерації тексту швидко приводить до зациклювання, якого можна уникнути якщо вибирати наступні слова випадковим чином.
def generate_model(cfdist, word, num=15):
for i in range(num):
print word,
word = cfdist[word].max()
text = nltk.corpus.genesis.words('english-kjv.txt')
bigrams = nltk.bigrams(text)
cfd = nltk.ConditionalFreqDist(bigrams)
>>> print cfd['living']
<FreqDist: 'creature': 7, 'thing': 4, 'substance': 2, ',': 1, '.': 1, 'soul': 1>
>>> generate_model(cfd, 'living')
living creature that he said , and the land of the land of the land
Інший тип даних Python - словники. Словники іноді можна зустріти в інших мовах програмування, як "асоціативні блоки пам'яті" або "асоціативні масиви". На відміну від послідовностей, які індексуються за допомогою діапазону чисел, словники індексуються ключами, які можуть бути будь-яким незмінним типом; рядки і числа можуть завжди бути використані як ключі. Кортежі можуть використовуватися як ключі, якщо вони містять лише стрічки, числа, або кортежі; якщо кортеж містить будь-який змінний об'єкт або безпосередньо чи побічно, то кортеж не може використовуватися як ключ. Ви не можете використовувати списки як ключі, оскільки списки можна змінити в словнику через методи, такі як append() і extend() або можна змінити зрізами чи індексованими призначеннями
Словник по суті є неврегульованим набором ключів: ключ завжди виконує вимогу унікальності (в межах одного словника). Пара фігурних дужок створює порожній словник: {. Розміщення відокремленого комами списку пар key:value в межах фігурних дужок додає початкові пари key:value до словника; описаний прийом також допустимий при виведенні словника на друк.
Основні операції над словником - збереження значення з деяким ключем і витягання значення, за вказаним ключем. Також можливо видалити пару key:value за допомогою del. Якщо Ви зберігаєте ключ, який знаходиться вже у використанні, про старе значення, що пов'язане з цим ключем, інтерпретатор забуває. При спробі звернеться до такого неіснуючого ключа - виникне помилка.
Метод keys() об'єкту словник повертає список всіх ключів, використовуваних в словнику, в довільному порядку (якщо Ви хочете сортувати ключі, слід застосувати метод sort() для списку ключів). Перевірка, чи знаходиться єдиний ключ в словнику, слід використовувати метод has_key() словника.
Тут приведений маленький приклад, використання словника:
>>> tel = {'jack': 4098, 'sape': 4139}
>>> tel['guido']= 4127
>>> tel
{'sape': 4139, 'guido': 4127, 'jack': 4098}
>>> tel['jack']
4098
>>> del tel['sape']
>>> tel['irv']= 4127
>>> tel
{'guido': 4127, 'irv': 4127, 'jack': 4098}
>>> tel.keys()
['guido', 'irv', 'jack']
>>> tel.has_key('guido')
True
>>> 'guido' in tel
True
dict() конструктор формує словник безпосередньо із списків пар "ключ:значення", збережених як кортежі. Коли пари формують шаблон, останній вноситься до списку для використання, шаблони можна стисло визначити із списками ключових значень.
>>> dict([('sape', 4139), ('guido', 4127), ('jack', 4098)])
{'sape': 4139, 'jack': 4098, 'guido': 4127}
>>> dict([(x, x**2) for x in (2, 4, 6)]) # безпосереднє використання списку
{2: 4, 4: 16, 6: 36}
Коли ключі - прості стрічки, іноді простіше визначати такі пари, що використовують параметри з ключами:
>>> dict(sape=4139, guido=4127, jack=4098)
{'sape': 4139, 'jack': 4098, 'guido': 4127}
Лексичний ресурс або просто словник це набір слів тa/або словосполучень, які асоціюються з такою інформацією, як частина мови та опис значення. Лексичні ресурси є вторинними по відношенню до текстів і зазвичай створюються і вдосконалюються з використанням текстів. Наприклад, якщо визначити текст my_text тоді vocab = sorted(set(my_text)) побудує словник тексту my_text, word_freq = FreqDist(my_text) визначить частоту кожного слова в тексті. vocab та word_freq приклад простих лексичних ресурсів. Так само конкорданс дає інформацію про використання слів і ця інформація може бути використана при побудові словників. Стандартна термінологія для словників (англ. мова) представлена на Рис.1. Словникова стаття містить основне слово (лему), та відповідну інформацію (частина мови значення слова).
Рис.1. Термінологія англійської мови для записів словників.
Найпростіший словник це відсортований список слів. Досконаліші словники містять складну структуру записів та звязків між ними. В цій лабораторні роботі будуть розглянуті лексичні ресурси, які розповсюджуються разом з NLTK.
NLTK розповсюджується з деякими корпусами, які насправді є списками слів. Корпус words це файл з Unix, який використовується для перевірки правопису. Цей список можна використати для знаходження незвичних та написаних з помилками слів в корпусі текстів, як показано в наступному прикладі:
def unusual_words(text):
text_vocab = set(w.lower() for w in text if w.isalpha())
english_vocab = set(w.lower() for w in nltk.corpus.words.words())
unusual = text_vocab.difference(english_vocab)
return sorted(unusual)
>>> unusual_words(nltk.corpus.gutenberg.words('austen-sense.txt'))
['abbeyland', 'abhorrence', 'abominably', 'abridgement', 'accordant', 'accustomary',
'adieus', 'affability', 'affectedly', 'aggrandizement', 'alighted', 'allenham',
'amiably', 'annamaria', 'annuities', 'apologising', 'arbour', 'archness', ...]
>>> unusual_words(nltk.corpus.nps_chat.words())
['aaaaaaaaaaaaaaaaa', 'aaahhhh', 'abou', 'abourted', 'abs', 'ack', 'acros',
'actualy', 'adduser', 'addy', 'adoted', 'adreniline', 'ae', 'afe', 'affari', 'afk',
'agaibn', 'agurlwithbigguns', 'ahah', 'ahahah', 'ahahh', 'ahahha', 'ahem', 'ahh', ...]
Ця програма працює за принципом фільтра. Спочатку створюється набір (словник) слів тексту, а далі з цього списку видаляються всі слова, які є в корпусі words.
В NLTK також включений корпус стоп-слів (незначущі слова). Ці слова часто зустрічаються в текстах, але переважно не мають окремого лексичного значення і переважно видаляються з тексту при його подальшій обробці.
>>> from nltk.corpus import stopwords
>>> stopwords.words('english')
['a', "a's", 'able', 'about', 'above', 'according', 'accordingly', 'across',
'actually', 'after', 'afterwards', 'again', 'against', "ain't", 'all', 'allow',
'allows', 'almost', 'alone', 'along', 'already', 'also', 'although', 'always', ...]
Можна визначити функцію для визначення, який відсоток слів тексту не належить до незначущих слів.
>>> def content_fraction(text):
... stopwords = nltk.corpus.stopwords.words('english')
... content = [w for w in text if w.lower() not in stopwords]
... return len(content) / len(text)
...
>>> content_fraction(nltk.corpus.reuters.words())
0.65997695393285261
За допомогою списку стоп-слів відкинуто третину слів з тексту. Дана програма працює з двома видами корпусів: текстовим корпусом і лексичним ресурсом-словником.
Рис.2. Приклад головоломки
Список слів (корпус words) можна використати для розвязування головоломки, що зображена на Рис.2. Наступна програма в циклі переглядає всі слова і перевіряє їх на відповідність умовам задачі. Перевірки чи є в слові обовязкова літера #2 та обмеження довжини слова #1 реалізувати просто. Складніше перевірити інші літери слова, особливо з врахуванням що одна з них може зустрічатися два рази (v). Така задача вирішується використанням методу порівняння класу FreqDist #3. Частота букв у слові має бути менше або дорівнювати частоті букв з умови задачі.
>>> puzzle_letters = nltk.FreqDist('egivrvonl')
>>> obligatory = 'r'
>>> wordlist = nltk.corpus.words.words()
>>> [w for w in wordlist if len(w) >= 6 #1
... and obligatory in w #2
... and nltk.FreqDist(w) <= puzzle_letters] #3
['glover', 'gorlin', 'govern', 'grovel', 'ignore', 'involver', 'lienor',
'linger', 'longer', 'lovering', 'noiler', 'overling', 'region', 'renvoi',
'revolving', 'ringle', 'roving', 'violer', 'virole']
Наступний корпус NLTK це корпус імен, обємом 8000 одиниць, які поділені на категорії за родами (чоловічим та жіночим). В наступному прикладі здійснюється пошук імен, які зустрічаються в обох категоріях, тобто імен, які належать і жінкам і чоловікам.
>>> names = nltk.corpus.names
>>> names.fileids()
['female.txt', 'male.txt']
>>> male_names = names.words('male.txt')
>>> female_names = names.words('female.txt')
>>> [w for w in male_names if w in female_names]
['Abbey', 'Abbie', 'Abby', 'Addie', 'Adrian', 'Adrien', 'Ajay', 'Alex', 'Alexis',
'Alfie', 'Ali', 'Alix', 'Allie', 'Allyn', 'Andie', 'Andrea', 'Andy', 'Angel',
'Angie', 'Ariel', 'Ashley', 'Aubrey', 'Augustine', 'Austin', 'Averil', ...]
Переважно імена, які закінчуються на букву «а» належать жінкам. Для перевірки цього твердження можна побудувати умовний частотний розподіл і переглянути графічне зображення цього розподілу Рис.3.
>>> cfd = nltk.ConditionalFreqDist(
... (fileid, name[-1])
... for fileid in names.fileids()
... for name in names.words(fileid))
>>> cfd.plot()
Рис.3. Умовний частотний розподіл останніх букв чоловічих та жіночих імен.
Більш багатим лінгвістичним ресурсом може бути словник де кожному слову поставлена у відповідність певна інформація. NLTK включає CMU Pronouncing Dictionary американського варіанту англійської , який розроблений для використання в синтезаторах мови.
>>> entries = nltk.corpus.cmudict.entries()
>>> len(entries)
127012
>>> for entry in entries[39943:39951]:
... print entry
...
('fir', ['F', 'ER1'])
('fire', ['F', 'AY1', 'ER0'])
('fire', ['F', 'AY1', 'R'])
('firearm', ['F', 'AY1', 'ER0', 'AA2', 'R', 'M'])
('firearm', ['F', 'AY1', 'R', 'AA2', 'R', 'M'])
('firearms', ['F', 'AY1', 'ER0', 'AA2', 'R', 'M', 'Z'])
('firearms', ['F', 'AY1', 'R', 'AA2', 'R', 'M', 'Z'])
('fireball', ['F', 'AY1', 'ER0', 'B', 'AO2', 'L'])
Кожному слову в цьому словнику відповідає список фонетичних кодів окремих позначень для кожного звуку(фон). Бачимо що слово “fire” в американській англійській має два варіанти вимови (односкладний та двоскладний). Позначення в CMU Pronouncing Dictionary детально описані у http://en.wikipedia.org/wiki/Arpabet.
Кожен запис у словнику складається з двох частин, кожна з яких може оброблятися індивідуально завдяки більш складному варіанту for оператора. Замість entry в операторі for entry in entries: записуємо дві змінні word, pron (#1) . В циклі на кожному кроці word відповідає першій частині запису а pron другій. Програма переглядає словник а пошуку записів, вимова яких містить три частини #2. Якщо ця умова справджується значення змінної pron присвоюється новим змінним ph1, ph2, ph3 #3.
>>> for word, pron in entries: #1
... if len(pron) == 3: #2
... ph1, ph2, ph3 = pron #3
... if ph1 == 'P' and ph3 == 'T':
... print word, ph2,
...
pait EY1 pat AE1 pate EY1 patt AE1 peart ER1 peat IY1 peet IY1 peete IY1 pert ER1
pet EH1 pete IY1 pett EH1 piet IY1 piette IY1 pit IH1 pitt IH1 pot AA1 pote OW1
pott AA1 pout AW1 puett UW1 purt ER1 put UH1 putt AH1
Наступний приклад показує використання аналогічного оператора for в спискових висловлюваннях. Ця програма шукає слова у вимові яких на кінці є звуки аналогічні до nicks. Таку програму можна використовувати для пошуку рим для заданих слів.
>>> syllable = ['N', 'IH0', 'K', 'S']
>>> [word for word, pron in entries if pron[-4:] == syllable]
["atlantic's", 'audiotronics', 'avionics', 'beatniks', 'calisthenics', 'centronics',
'chetniks', "clinic's", 'clinics', 'conics', 'cynics', 'diasonics', "dominic's",
'ebonics', 'electronics', "electronics'", 'endotronics', "endotronics'", 'enix', ...]
Результати роботи програми показують відмінності у написанні деяких закінчень з однаковою вимовою(nics, niks, nix, ntic's).
Виконати самостійно
Здійснити аналіз наступних прикладів.
>>> [w for w, pron in entries if pron[-1] == 'M' and w[-1] == 'n']
['autumn', 'column', 'condemn', 'damn', 'goddamn', 'hymn', 'solemn']
>>> sorted(set(w[:2] for w, pron in entries if pron[0] == 'N' and w[0] != 'n'))
['gn', 'kn', 'mn', 'pn']
В позначеннях звуків (фонах) використовуються цифри для позначення наголосів. Наступний приклад дозволяє доступитися до цифрових позначень і знайти у словнику слова за відповідними шаблонами наголосів. В цьому прикладі потрібно звернути увагу на подвійне використання оператора for.
>>> def stress(pron):
... return [char for phone in pron for char in phone if char.isdigit()]
>>> [w for w, pron in entries if stress(pron) == ['0', '1', '0', '2', '0']]
['abbreviated', 'abbreviating', 'accelerated', 'accelerating', 'accelerator',
'accentuated', 'accentuating', 'accommodated', 'accommodating', 'accommodative',
'accumulated', 'accumulating', 'accumulative', 'accumulator', 'accumulators', ...]
>>> [w for w, pron in entries if stress(pron) == ['0', '2', '0', '1', '0']]
['abbreviation', 'abbreviations', 'abomination', 'abortifacient', 'abortifacients',
'academicians', 'accommodation', 'accommodations', 'accreditation', 'accreditations',
'accumulation', 'accumulations', 'acetylcholine', 'acetylcholine', 'adjudication', ...]
Використовуючи умовний частотний розподіл можна знайти слова, які мають подібну вимову. Знайдемо слова перша буква яких Р , які складаються з трьох звуків #2 і згрупуємо їх за першим і останнім звуками #1.
>>> p3 = [(pron[0]+'-'+pron[2], word)
... for (word, pron) in entries
... if pron[0] == 'P' and len(pron) == 3]
>>> cfd = nltk.ConditionalFreqDist(p3)
>>> for template in cfd.conditions():
... if len(cfd[template]) > 10:
... words = cfd[template].keys()
... wordlist = ' '.join(words)
... print template, wordlist[:70] + "..."
...
P-CH perch puche poche peach petsche poach pietsch putsch pautsch piche pet...
P-K pik peek pic pique paque polk perc poke perk pac pock poch purk pak pa...
P-L pil poehl pille pehl pol pall pohl pahl paul perl pale paille perle po...
P-N paine payne pon pain pin pawn pinn pun pine paign pen pyne pane penn p...
P-P pap paap pipp paup pape pup pep poop pop pipe paape popp pip peep pope...
P-R paar poor par poore pear pare pour peer pore parr por pair porr pier...
P-S pearse piece posts pasts peace perce pos pers pace puss pesce pass pur...
P-T pot puett pit pete putt pat purt pet peart pott pett pait pert pote pa...
P-Z pays p.s pao's pais paws p.'s pas pez paz pei's pose poise peas paiz p...
Словник вимови можна використати для обробки тексту. У наступному прикладі програма знаходить вимову всіх зазначених слів.
>>> text = ['natural', 'language', 'processing']
>>> [ph for w in text for ph in prondict[w][0]]
['N', 'AE1', 'CH', 'ER0', 'AH0', 'L', 'L', 'AE1', 'NG', 'G', 'W', 'AH0', 'JH',
'P', 'R', 'AA1', 'S', 'EH0', 'S', 'IH0', 'NG']
Інший словник в NLTK це порівняльний словник (Swadesh wordlists), який містить 200 спільних слів для 24 мов. Мови ідентифікуються за двосимвольними кодами (ISO 639).
>>> from nltk.corpus import swadesh
>>> swadesh.fileids()
['be', 'bg', 'bs', 'ca', 'cs', 'cu', 'de', 'en', 'es', 'fr', 'hr', 'it', 'la', 'mk',
'nl', 'pl', 'pt', 'ro', 'ru', 'sk', 'sl', 'sr', 'sw', 'uk']
>>> swadesh.words('en')
['I', 'you (singular), thou', 'he', 'we', 'you (plural)', 'they', 'this', 'that',
'here', 'there', 'who', 'what', 'where', 'when', 'how', 'not', 'all', 'many', 'some',
'few', 'other', 'one', 'two', 'three', 'four', 'five', 'big', 'long', 'wide', ...]
До подібних слів з різних мов можна доступитися за допомогою метода entries(), аргументом якого є список мов.
>>> fr2en = swadesh.entries(['fr', 'en'])
>>> fr2en
[('je', 'I'), ('tu, vous', 'you (singular), thou'), ('il', 'he'), ...]
В наступному прикладі порівнюються слова романських і германських мов.
>>> languages = ['en', 'de', 'nl', 'es', 'fr', 'pt', 'la']
>>> for i in [139, 140, 141, 142]:
... print swadesh.entries(languages)[i]
...
('say', 'sagen', 'zeggen', 'decir', 'dire', 'dizer', 'dicere')
('sing', 'singen', 'zingen', 'cantar', 'chanter', 'cantar', 'canere')
('play', 'spielen', 'spelen', 'jugar', 'jouer', 'jogar, brincar', 'ludere')
('float', 'schweben', 'zweven', 'flotar', 'flotter', 'flutuar, boiar', 'fluctuare')
WordNet, це семантично орієнтований словник англійської мови, подібний до традиційних тезаурусів але з більш багатою структурою. У WordNet слова групуються у набори синонімів синсети, кожен із своїм визначенням і звязками з іншими синсетами. WordNet 3.0 розповсюджується разом з NLTK і містить 155287 слів та 117659 синсетів. Хоча WordNet розроблявся для психолінгвістики - цей словник широко використовується в NLP та в задачах інформаційного пошуку. Розробки для інших мов проводяться на основі документації, яка наведена у http://www.globalwordnet.org/.
Розглянемо наступне речення:
(1) Benz is credited with the invention of motorcar.
Якщо замінити слово motorcar на automobile зміст речення не зміниться.
(2) Benz is credited with the invention of automobile .
Можна вважати, що оскільки заміна слів не вплинула на зміст речень то ці слова синоніми. Для одержання значення слова потрібно вибрати до якої частини мови воно належить. WordNet містить чотири словники (іменники, дієслова, прикметники, прислівники ). Знайдемо слово motorcar у словнику іменників:
>>> from nltk.corpus import wordnet as wn
>>> wn.synsets('motorcar')
[Synset('car.n.01')]
Тут, вираз wordnet as wn позначає, що в подальшому для звертання до словника wordnet буде використана коротша назва wn.
Слово motorcar має одне можливе значення і воно ідентифікується як car.n.01 перший сенс іменника car. car.n.01 називають синсетом множиною синонімічних слів.
>>> wn.synset('car.n.01').lemma_names
['car', 'auto', 'automobile', 'machine', 'motorcar']
Слова в синсет обєднані за спільним значенням, яке є однакове для всіх слів. В синсеті вказується текстовий опис цього значення та приклад вживання слів з синсету.
>>> wn.synset('car.n.01').definition
'a motor vehicle with four wheels; usually propelled by an internal combustion engine'
>>> wn.synset('car.n.01').examples
['he needs a car to get to work']
Для уникнення двозначності слова з син сету можна ідентифікувати як car.n.01.automobile, car.n.01.motorcar . Такі пари, як синсет і слово називають лемою. Можна переглянути всі леми даного синсету #1, переглянути окрему лему #2, відповідний лемі синсет #3, та імя леми #4.
>>> wn.synset('car.n.01').lemmas
#1 перегляд всіх лем даного синсету
[Lemma('car.n.01.car'), Lemma('car.n.01.auto'), Lemma('car.n.01.automobile'),
Lemma('car.n.01.machine'), Lemma('car.n.01.motorcar')]
>>> wn.lemma('car.n.01.automobile')
#2 перегляд окремої леми
Lemma('car.n.01.automobile')
>>> wn.lemma('car.n.01.automobile').synset
#3 перегляд синсету відповідної леми
Synset('car.n.01')
>>> wn.lemma('car.n.01.automobile').name #4 дізнатися імя леми
'automobile'
Слова automobile та motorcar є однозначні і входять тільки в один синсет. Слово car багатозначне і входить в пять синсетів.
>>> wn.synsets('car')
[Synset('car.n.01'), Synset('car.n.02'), Synset('car.n.03'), Synset('car.n.04'),
Synset('cable_car.n.01')]
>>> for synset in wn.synsets('car'):
... print synset.lemma_names
...
['car', 'auto', 'automobile', 'machine', 'motorcar']
['car', 'railcar', 'railway_car', 'railroad_car']
['car', 'gondola']
['car', 'elevator_car']
['cable_car', 'car']
До всіх лем слова car можна доступитися наступним чином:
>>> wn.lemmas('car')
[Lemma('car.n.01.car'), Lemma('car.n.02.car'), Lemma('car.n.03.car'),
Lemma('car.n.04.car'), Lemma('cable_car.n.01.car')]
Синсети відповідають абстрактним поняттям, які можуть мати або не мати відповідних слів. Ці поняття звязуються разом в ієрархії. Деякі поняття Entity, State, Event є загальними і їх називають унікальними початковими поняттями. Інші є більше специфічними. Частина ієрархії понять наведена на рис.4. Лінії між вузлами вказують на звязки (гіперонім\гіпонім), пунктирна лінія вказує, що artefact не є безпосереднім гіперонімом motorcar.
Рис.4. Фрагмент ієрархії понять
WordNet дозволяє легко переміщатися між поняттями. Наприклад для поняття motorcar ми можемо переглянути поняття, які є більш специфічними (гіпонім):
>>> motorcar = wn.synset('car.n.01')
>>> types_of_motorcar = motorcar.hyponyms()
>>> types_of_motorcar[26]
Synset('ambulance.n.01')
>>> sorted([lemma.name for synset in types_of_motorcar for lemma in synset.lemmas])
['Model_T', 'S.U.V.', 'SUV', 'Stanley_Steamer', 'ambulance', 'beach_waggon',
'beach_wagon', 'bus', 'cab', 'compact', 'compact_car', 'convertible',
'coupe', 'cruiser', 'electric', 'electric_automobile', 'electric_car',
'estate_car', 'gas_guzzler', 'hack', 'hardtop', 'hatchback', 'heap',
'horseless_carriage', 'hot-rod', 'hot_rod', 'jalopy', 'jeep', 'landrover',
'limo', 'limousine', 'loaner', 'minicar', 'minivan', 'pace_car', 'patrol_car',
'phaeton', 'police_car', 'police_cruiser', 'prowl_car', 'race_car', 'racer',
'racing_car', 'roadster', 'runabout', 'saloon', 'secondhand_car', 'sedan',
'sport_car', 'sport_utility', 'sport_utility_vehicle', 'sports_car', 'squad_car',
'station_waggon', 'station_wagon', 'stock_car', 'subcompact', 'subcompact_car',
'taxi', 'taxicab', 'tourer', 'touring_car', 'two-seater', 'used-car', 'waggon',
'wagon']
Аналогічно можна піднятися по ієрархії і переглянути більш широкі поняття ніж motorcar (гіпероніми). Деякі слова мають декілька шляхів вверх, ці слова можуть класифікуватися більш ніж одним способом. Від car.n.01 до entity.n.01 є два шляхи оскільки wheeled_vehicle.n.01 може розглядатися як vehicle та container.
>>> motorcar.hypernyms()
[Synset('motor_vehicle.n.01')]
>>> paths = motorcar.hypernym_paths()
>>> len(paths)
2
>>> [synset.name for synset in paths[0]]
['entity.n.01', 'physical_entity.n.01', 'object.n.01', 'whole.n.02', 'artifact.n.01',
'instrumentality.n.03', 'container.n.01', 'wheeled_vehicle.n.01',
'self-propelled_vehicle.n.01', 'motor_vehicle.n.01', 'car.n.01']
>>> [synset.name for synset in paths[1]]
['entity.n.01', 'physical_entity.n.01', 'object.n.01', 'whole.n.02', 'artifact.n.01',
'instrumentality.n.03', 'conveyance.n.03', 'vehicle.n.01', 'wheeled_vehicle.n.01',
'self-propelled_vehicle.n.01', 'motor_vehicle.n.01', 'car.n.01']
Початкове кореневе поняття для синсета можна переглянути наступним чином.
>>> motorcar.root_hypernyms()
[Synset('entity.n.01')]
Таблиця 1 містить список найбільш важливих типів звязків, які реалізовані у WordNet. Таблиця 2 містить повний список звязків іменників.
Таблиця 1
Hypernym |
Узагальнення |
Тварини є гіпернімом собаки |
Hyponym |
Деталізація |
Собака є гіпонімом тварин |
Meronym |
Частина від |
Двері є меронімом будинку |
Holonym |
Містить складові |
Будинок є холонімом дверей |
Synonym |
Подібне значення |
Машина є синонімом автомобіля |
Antonym |
Протилежне значення |
Подобається є антонімом не подобається |
Entailment |
Необхідна дія |
Крок є ентейлментом ходи |
Таблиця 2
Relation |
Also Called |
Definition |
Example |
Hypernym |
Superordinate |
From concepts to superordinates |
Breakfast meal |
Hyponym |
Subordinate |
From concepts to subtypes |
Meal Lunch |
Instance Hypernym |
Instance |
From instances to their concepts |
Austen Author |
Instance Hyponym |
Has-Instance |
From concepts to concepts instances |
Composer Bach |
Member Meronym |
Has-Member |
From groups to their members |
Faculty Professor |
Member Holonym |
Member-Of |
From members to their groups |
Copilot Crew |
Part Meronym |
Has-Part |
From wholes to parts |
Table Leg |
Part Holonym |
Part-Of |
From parts to wholes |
Course Meal |
Substance Meronym |
From substances to their subparts |
Water Oxyden |
|
Substance Holonym |
From parts of substances to wholes |
Gin Martini |
|
Antonym |
Semantic opposition between lemmas |
Leader Follower |
|
Derivationally Related Form |
Lemmas w/same morphological root |
Destruction Destroy |
Гіперніми та гіпоніми називають лексичними звязками тому що вони повязують один синсет з іншим. Ці два звязки вказують на рух вверх-вниз в ієрархії «is-a». Інший можливий шлях в ієрархії WordNet це від предмету до його складових (меронім), або до поняття яке містить предмет в собі (голоніми). Наприклад, частини дерева стовбур, крона та ін. part_meronyms() . Речовина з якого дерево зроблено включає heartwood та sapwood; - substance_meronyms(). Багато дерев утворюють ліс - member_holonyms()
>>> wn.synset('tree.n.01').part_meronyms()
[Synset('burl.n.02'), Synset('crown.n.07'), Synset('stump.n.01'),
Synset('trunk.n.01'), Synset('limb.n.02')]
>>> wn.synset('tree.n.01').substance_meronyms()
[Synset('heartwood.n.01'), Synset('sapwood.n.01')]
>>> wn.synset('tree.n.01').member_holonyms()
[Synset('forest.n.01')]
Прикладом складних випадків лексичних звязків може бути слово mint , яке має декілька близьких значень. Бачимо, що mint.n.04 є частиною mint.n.02 та речовиною з якої зроблено mint.n.05.
>>> for synset in wn.synsets('mint', wn.NOUN):
... print synset.name + ':', synset.definition
...
batch.n.02: (often followed by `of') a large number or amount or extent
mint.n.02: any north temperate plant of the genus Mentha with aromatic leaves and
small mauve flowers
mint.n.03: any member of the mint family of plants
mint.n.04: the leaves of a mint plant used fresh or candied
mint.n.05: a candy that is flavored with a mint oil
mint.n.06: a plant where money is coined by authority of the government
>>> wn.synset('mint.n.04').part_holonyms()
[Synset('mint.n.02')]
>>> wn.synset('mint.n.04').substance_holonyms()
[Synset('mint.n.05')]
Для дієслів характерні звязки подібні до наступних:
>>> wn.synset('walk.v.01').entailments()
[Synset('step.v.01')]
>>> wn.synset('eat.v.01').entailments()
[Synset('swallow.v.01'), Synset('chew.v.01')]
>>> wn.synset('tease.v.03').entailments()
[Synset('arouse.v.07'), Synset('disappoint.v.01')]
Дія walking передбачає дію stepping - walking спричиняє (entails) stepping.
Ще один тип звязків представлений в WordNet це антоніми:
>>> wn.lemma('supply.n.02.supply').antonyms()
[Lemma('demand.n.02.demand')]
>>> wn.lemma('rush.v.01.rush').antonyms()
[Lemma('linger.v.04.linger')]
>>> wn.lemma('horizontal.a.01.horizontal').antonyms()
[Lemma('vertical.a.01.vertical'), Lemma('inclined.a.02.inclined')]
>>> wn.lemma('staccato.r.01.staccato').antonyms()
[Lemma('legato.r.01.legato')]
Синсети звязані між собою складною мережею лексичних звязків. Для певного синсету можна переглянути звязки у WordNet і знайти синсети, які з ним звязані за змістом. Інформація про семантичні взаємозвязки між словами цінна при класифікації текстів.
Кожен синсет має один або більше шляхів за яким він зводиться до ключового поняття entity.n.01. Два синсети можуть мати спільне ключове поняття і ми нижче за ієрархією це ключове поняття тим ближчі між собою ці два синсети.
>>> right = wn.synset('right_whale.n.01')
>>> orca = wn.synset('orca.n.01')
>>> minke = wn.synset('minke_whale.n.01')
>>> tortoise = wn.synset('tortoise.n.01')
>>> novel = wn.synset('novel.n.01')
>>> right.lowest_common_hypernyms(minke)
[Synset('baleen_whale.n.01')]
>>> right.lowest_common_hypernyms(orca)
[Synset('whale.n.02')]
>>> right.lowest_common_hypernyms(tortoise)
[Synset('vertebrate.n.01')]
>>> right.lowest_common_hypernyms(novel)
[Synset('entity.n.01')]
Зрозуміло що whale це чітко визначене поняття, тоді як vertebrate є більш загальним а entity найбільш загальним. Можна оцінити «загальність» поняття визначивши глибину кожного синсета.
>>> wn.synset('baleen_whale.n.01').min_depth()
14
>>> wn.synset('whale.n.02').min_depth()
13
>>> wn.synset('vertebrate.n.01').min_depth()
8
>>> wn.synset('entity.n.01').min_depth()
0
Семантична подібність двох понять повязана з довжиною шляху між цими поняттями в WordNet . Пакет wordnet містить багато засобів для здійснення таких вимірювань (Leacock-Chodorow, Wu-Palmer, Resnik, Jiang-Conrath, Lin ). Наприклад path_similarity (присвоює значення від 0 до 1) базується на найкоротшому шляху, який поєднує поняття за ієрархією гіперонімів (-1 означає що шлях (спільний гіперонім) не знайдено).
>>> right.path_similarity(minke)
0.25
>>> right.path_similarity(orca)
0.16666666666666666
>>> right.path_similarity(tortoise)
0.076923076923076927
>>> right.path_similarity(novel)
0.043478260869565216
Сьогодні ми вивчили:
1. Ознайомитися з теоретичними відомостями.
2. Виконати приклади, які використовуються в теоретичних відомостях.
3. Виконати наступні вправи:
4. Підготувати і оформити звіт.
Варіант |
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
Номери завдань |
1 |
2 |
1 |
2 |
1 |
2 |
1 |
2 |
1 |
2 |
1 |
1 |
2 |
1 |
2 |
3 |
5 |
5 |
3 |
3 |
5 |
5 |
3 |
3 |
5 |
5 |
3 |
5 |
5 |
3 |
|
4 |
6 |
4 |
6 |
6 |
4 |
4 |
4 |
6 |
4 |
6 |
6 |
4 |
4 |
4 |
|
7 |
8 |
9 |
9 |
7 |
8 |
7 |
8 |
9 |
9 |
7 |
8 |
||||
10 |
11 |
12 |
13 |
10 |
11 |
12 |
13 |
10 |
11 |
12 |
10 |
11 |
12 |
13 |
|
14 |
15 |
16 |
17 |
14 |
15 |
16 |
17 |
14 |
15 |
16 |
14 |
15 |
16 |
17 |
|
Варіант |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
Номери завдань |
1 |
2 |
1 |
2 |
2 |
1 |
2 |
1 |
2 |
1 |
2 |
1 |
2 |
1 |
2 |
3 |
5 |
5 |
3 |
5 |
5 |
3 |
3 |
5 |
5 |
3 |
3 |
5 |
5 |
3 |
|
4 |
6 |
4 |
6 |
6 |
4 |
4 |
6 |
6 |
4 |
6 |
6 |
4 |
4 |
6 |
|
7 |
8 |
9 |
9 |
7 |
8 |
7 |
8 |
9 |
9 |
7 |
8 |
8 |
7 |
9 |
|
10 |
11 |
12 |
13 |
11 |
12 |
13 |
10 |
11 |
12 |
13 |
10 |
11 |
12 |
13 |
|
14 |
15 |
16 |
17 |
15 |
16 |
17 |
14 |
15 |
16 |
17 |
14 |
15 |
16 |
17 |
|
А также другие работы, которые могут Вас заинтересовать | |||
19035. | Спин элементарных частиц. Спиновые волновые функции и операторы спина | 1.1 MB | |
Лекция 17 Спин элементарных частиц. Спиновые волновые функции и операторы спина Рассмотрим составную частицу состоящую из двух элементарных частиц и совершающую некоторое пространственное движение примером такой составной частицы может быть ядро дейтерия состо | |||
19036. | Спин 1/2. Спиновые функции, операторы спина. Матрицы Паули и их свойства. Разложение по спиновым функциям | 1.1 MB | |
Лекция 18 Спин 1/2. Спиновые функции операторы спина. Матрицы Паули и их свойства. Разложение по спиновым функциям Целый ряд элементарных частиц электроны нейтроны протоны и другие обладают спином . По этой причине рассмотрим подробно свойства спиновых функций и | |||
19037. | Собственный магнитный момент. Уравнение Паули. Движение заряженной частицы в магнитном поле. Уровни Ландау | 416.5 KB | |
Лекция 19 Собственный магнитный момент. Уравнение Паули. Движение заряженной частицы в магнитном поле. Уровни Ландау Многие элементарные частицы в том числе и незаряженные имеют магнитный момент не связанный с ее движением в пространстве а связанный с внутренними ... | |||
19038. | Сложение моментов. Коэффициенты Клебша-Гордана | 1.3 MB | |
Лекция 20 Сложение моментов. Коэффициенты КлебшаГордана Поскольку в классической механике суммарный момент импульса системы из двух частиц равен векторной сумме моментов частиц квантовомеханический оператор суммарного момента двух частиц определяется как | |||
19039. | Примеры построения собственных функций оператора суммарного момента двух частиц. Сложение двух спинов ½. Классификация спиновых функций в системе из двух частиц | 660.5 KB | |
Лекция 21 Примеры построения собственных функций оператора суммарного момента двух частиц. Сложение двух спинов . Классификация спиновых функций в системе из двух частиц Покажем как вычисляются коэффициенты КлебшаГордана на нескольких примера. Пусть система из ду... | |||
19040. | Квазиклассическое приближение. Квазиклассические решения уравнения Шредингера, сшивка квазиклассических решений | 664.5 KB | |
Лекция 22 Квазиклассическое приближение. Квазиклассические решения уравнения Шредингера сшивка квазиклассических решений Число случаев когда удается точно решить стационарное уравнение Шредингера то есть найти собственные значения и собственные функции операт... | |||
19041. | Правило квантования Бора-Зоммерфельда. Примеры. Квазиклассический коэффициент прохождения через барьер. Вероятность альфа распада в квазиклассическом приближении | 384.5 KB | |
Лекция 23 Правило квантования БораЗоммерфельда. Примеры. Квазиклассический коэффициент прохождения через барьер. Вероятность альфа распада в квазиклассическом приближении Квазиклассические решения и условия их сшивки в точках поворота позволяют получить в кв... | |||
19042. | Уравнение Томаса-Ферми | 127 KB | |
Лекция 24 Уравнение ТомасаФерми Распределение заряда и электрического поля в атомах с учетом взаимодействия электронов друг с другом проводятся методами самосогласованного поля. Эти расчеты очень сложны и громоздки особенно многоэлектронных атомов. Но как раз дл | |||
19043. | Теория стационарных возмущений для состояний дискретного спектра. Случай невырожденного спектра | 279 KB | |
Лекция 25 Теория стационарных возмущений для состояний дискретного спектра. Случай невырожденного спектра Точное решение стационарного уравнения Шредингера как правило представляет собой существенную математическую проблему и возможно только для простейших кв... | |||