4720

Використання Юнікоду при обробці текстів на мові Python

Лабораторная работа

Информатика, кибернетика и программирование

Мета робота Вивчення методів роботи з файлами на локальних дисках та з Інтернету. Використання Юнікоду при обробці текстів. Нормалізація текстів, стемінг, лематизація та сегментація. Короткі теоретичні відомості Виконання цієї лабо...

Украинкский

2012-11-25

852 KB

5 чел.

Мета робота

  1.  Вивчення методів роботи з файлами на локальних дисках та з Інтернету.
  2.  Використання Юнікоду при обробці текстів.
  3.  Нормалізація текстів, стемінг, лематизація та сегментація.

Короткі теоретичні відомості

Виконання цієї лабораторної роботи необхідно розпочати з:

>>> from __future__ import division

>>> import nltk, re, pprint

Корпуси текстів та тексти з Інтернету є важливими джерелами даних для здійснення лінгвістичних досліджень. Звичайно, якщо дослідник має власноруч зібрані тексти, то потрібні засоби для доступу до них.

В результаті виконання лабораторної роботи будуть вирішені наступні питання:

  1.  Як написати програму для доступу до текстів з локальних файлів та з Інтернету, які є необмеженими джерелами лінгвістичних даних?
  2.  Як поділити текст на окремі слова та розділові знаки, для одержання можливості проводити подальший аналіз тексту?
  3.  Як написати програму для представлення результатів роботи в певному форматі та зберегти їх у файлі?

1. Доступ до текстів з Інтернету та локальних дисків.

1.1. Електронні книжки

Частина електронних книжок з Project Gutenberg розповсюджується разом з NLTK у вигляді корпуса текстів. Для використання інших текстів з цього проекту можна переглянути каталог 25000 електронних книжок за адресою http://www.gutenberg.org/catalog/ та встановити адресу (URL) потрібного текстового файлу в ASCII кодуванні. 90% текстів в Project Gutenberg є англійською мовою, але він включає також тексти більше ніж 50-ма іншими мовами (каталонська, китайська, датська, фінська, французька, німецька, італійська, португальська, іспанська…).

Текст за номером 2554 це переклад англійською Crime and Punishment(Злочин і кара), і отримати доступ до тексту можна наступним чином:

>>> from urllib import urlopen

>>> url = "http://www.gutenberg.org/files/2554/2554.txt"

>>> raw = urlopen(url).read()

>>> type(raw)

<type 'str'>

>>> len(raw)

1176831

>>> raw[:75]

'The Project Gutenberg EBook of Crime and Punishment, by Fyodor Dostoevsky\r\n'

Виконання read() займає певний час протягом якого відбувається завантаження цієї великої книжки. При використанні проксі сервера для доступу до Інтернету, при необхідності, його параметри потрібно вказати:

>>> proxies = {'http': 'http://www.someproxy.com:3128'}

>>> raw = urlopen(url, proxies=proxies).read()

Текст книжки збережений як значення змінної raw. Змінна raw містить стрічку довжиною 1,176,831 символів. (Перевірити тип змінної можна скориставшись type(raw).) Стрічка яка відповідає вмісту книжки містить багато не цікавої для аналізу інформації: пробіли, пусті стрічки, межі стрічки. Символи  \r and \n , які є в тексті, це символи переводу каретки та початку нового рядка. Для подальшої роботи з текстом потрібно розділити текст на окремі слова та виділити розділові знаки. Такий процес називають токенізацією. При використанні програми токенізації з NLTK отримуємо список слів та розділових знаків.

>>> tokens = nltk.word_tokenize(raw)

>>> type(tokens)

<type 'list'>

>>> len(tokens)

255809

>>> tokens[:10]

['The', 'Project', 'Gutenberg', 'EBook', 'of', 'Crime', 'and', 'Punishment', ',', 'by']

Бібліотека NLTK використовувалась тільки на етапі токенізації і не використовувалась при доступі за адресою в Інтернеті та при читанні стрічки. Для подальшої роботи список перетворюється в NLTK текст і над ним можна здійснювати різноманітні операції:

>>> text = nltk.Text(tokens)

>>> type(text)

<type 'nltk.text.Text'>

>>> text[1020:1060]

['CHAPTER', 'I', 'On', 'an', 'exceptionally', 'hot', 'evening', 'early', 'in',

'July', 'a', 'young', 'man', 'came', 'out', 'of', 'the', 'garret', 'in',

'which', 'he', 'lodged', 'in', 'S', '.', 'Place', 'and', 'walked', 'slowly',

',', 'as', 'though', 'in', 'hesitation', ',', 'towards', 'K', '.', 'bridge', '.']

>>> text.collocations()

Katerina Ivanovna; Pulcheria Alexandrovna; Avdotya Romanovna; Pyotr

Petrovitch; Project Gutenberg; Marfa Petrovna; Rodion Romanovitch;

Sofya Semyonovna; Nikodim Fomitch; did not; Hay Market; Andrey

Semyonovitch; old woman; Literary Archive; Dmitri Prokofitch; great

deal; United States; Praskovya Pavlovna; Porfiry Petrovitch; ear rings

В побудованих колокаціях зустрічається Project Gutenberg, словосполучення, яке не міститься в тексті книжки. Завантажений текст з сайту містить метатекстову розмітку (інформацію про автора, про текст, про людей які готували електронний варіант та ін.). Ця інформація може бути, як на початку тексту так і в його кінці . Для роботи власне з текстом книжки потрібно в ручному режимі знайти межі цих додаткових даних і за допомогою зрізів доступитися до тексту.

>>> raw.find("PART I")

5303

>>> raw.rfind("End of Project Gutenberg's Crime")

1157681

>>> raw = raw[5303:1157681]

>>> raw.find("PART I")

0

Методи find() та rfind() ("пошук з кінця") допомагають знайти потрібні індекси для їх подальшого використання в зрізах. Значення зрізу переприсвоюється змінній raw.

1.2. Робота з HTML файлами.

Більшість текстів в Інтернеті є у вигляді HTML документів (файлів). Інтернет сторінки можна зберігати на диску у вигляді файлів і доступатися до них. Python також дозволяє працювати Інтернет сторінками безпосередньо використовуючи функцію urlopen. Для прикладу переглянемо текст з BBC News story з назвою Blondes to die out in 200 years:

>>> url = "http://news.bbc.co.uk/2/hi/health/2284783.stm"

>>> html = urlopen(url).read()

>>> html[:60]

'<!doctype html public "-//W3C//DTD HTML 4.0 Transitional//EN'

Текст, який вивели на екран містить HTML розмітку (мета теги, JavaScript, форми , таблиці). Вилучення тексту з HTML файлу доволі розповсюджена задача, яка в NLTK вирішується за допомогою функції nltk.clean_html(). Ця функція обробляє HTML стрічку і повертає текст у вигляді зручному для подальшої обробки (токенізації).

>>> raw = nltk.clean_html(html)

>>> tokens = nltk.word_tokenize(raw)

>>> tokens

['BBC', 'NEWS', '|', 'Health', '|', 'Blondes', "'", 'to', 'die', 'out', ...]

Видалення іншої небажаної інформації проводиться в ручному режимі, аналогічно до попередніх прикладів з електронними книжками.

>>> tokens = tokens[96:399]

>>> text = nltk.Text(tokens)

>>> text.concordance('gene')

they say too few people now carry the gene for blondes to last beyond the next tw

t blonde hair is caused by a recessive gene . In order for a child to have blonde

to have blonde hair , it must have the gene on both sides of the family in the gra

there is a disadvantage of having that gene or by chance . They don ' t disappear

ondes would disappear is if having the gene was a disadvantage and I do not think

1.3. Обробка результатів пошукових запитів.

Виконати самостійно: Здійсніть аналіз результатів пошуку в Інтернеті наступного словосполучення "the of" . Чи можна аналогічним чином знайти найчастотніші колокації англійської мови?

1.4. Обробка RSS стрічок

Блогосфера важливе джерело текстів, як формальних так і не формальних. З допомогою бібліотеки Python Universal Feed Parser, http://feedparser.org/, можна отримати доступ до вмісту блогів,  як показано у наступному прикладі:

>>> import feedparser

>>> llog = feedparser.parse("http://languagelog.ldc.upenn.edu/nll/?feed=atom")

>>> llog['feed']['title']

u'Language Log'

>>> len(llog.entries)

15

>>> post = llog.entries[2]

>>> post.title

u"He's My BF"

>>> content = post.content[0].value

>>> content[:70]

u'<p>Today I was chatting with three of our visiting graduate students f'

>>> nltk.word_tokenize(nltk.html_clean(content))

>>> nltk.word_tokenize(nltk.clean_html(llog.entries[2].content[0].value))

[u'Today', u'I', u'was', u'chatting', u'with', u'three', u'of', u'our', u'visiting',

u'graduate', u'students', u'from', u'the', u'PRC', u'.', u'Thinking', u'that', u'I',

u'was', u'being', u'au', u'courant', u',', u'I', u'mentioned', u'the', u'expression',

u'DUI4XIANG4', u'\u5c0d\u8c61', u'("', u'boy', u'/', u'girl', u'friend', u'"', ...]

1.5. Читання локальних файлів.

Для читання локальних файлів необхідно використовувати вбудовану функцію Python open() та read() метод. Якщо існує файл  document.txt, то змінній raw  можна присвоїти його вміст:

>>> f = open('document.txt')

>>> raw = f.read()

Якщо інтерпретатор не знайде файл, він видасть помилку, подібну до наступної:

>>> f = open('document.txt')

Traceback (most recent call last):

File "<pyshell#7>", line 1, in -toplevel-

f = open('document.txt')

IOError: [Errno 2] No such file or directory: 'document.txt'

Для перевірки чи дійсно файл є в потрібній директорії у графічному інтерфейсі IDLE використовується команда Open з пункту меню File. Можна також перевірити вміст директорії наступним чином:

>>> import os

>>> os.listdir('.')

Інша можлива проблема при читанні текстових файлів – це різні способи маркування нового рядка у файлах різних операційних систем. При виклику функція open() може містити другий параметр для контролю відкривання файлу open('document.txt', 'rU') („r” файл для читання, ”U” universal дозволяє ігнорувати різні способи, які використовуються для маркування нового рядка).

Для читання вмісту файлу можна використати багато різних методів. Метод read() , використаний до об’єкту файл (f), читає вміст файлу і представляє його стрічкою:

>>> f.read()

'Time flies like an arrow.\nFruit flies like a banana.\n'

Символ '\n' – це символ нового рядка.

Файл можна читати стрічка за стрічкою, використовуючи for-цикл і використовувати зріз [:-1] або метод strip() для видалення символів нового рядка:

>>> f = open('document.txt', 'rU')

>>> for line in f:

...     print line.strip()

Time flies like an arrow.

Fruit flies like a banana.

За допомогою цих методів також можна доступитися і до файлів з корпусів, які розповсюджуються з NLTK. Потрібно використати  nltk.data.find() для одержання шляху до будь-якого файлу корпуса, а далі відкривати та читати файл, як показано:

>>> path = nltk.data.find('corpora/gutenberg/melville-moby_dick.txt')

>>> raw = open(path, 'rU').read()

1.6. Ввід тексту з клавіатури.

Для вводу тексту з клавіатури (при взаємодії користувача з програмою) потрібно використати функцію raw_input(). Після збереження введеного тексту у змінній з ним можна працювати як зі звичайною стрічкою.

>>> s = raw_input("Enter some text: ")

Enter some text: On an exceptionally hot evening early in July

>>> print "You typed", len(nltk.word_tokenize(s)), "words."

You typed 8 words.

1.7. Схема роботи з текстами при їх початковій обробці

На Рис 1. представлена узагальнена, на основі вищевикладеного, схема початкової обробки текстів природною мовою. Початкова обробка текстів природною мовою може містити наступні етапи: відкривання та читання тексту з Інтернету, видалення розмітки, токенізація, перетворення тексту в NLTK текст.

Коли відбувається доступ до вмісту файлу чи вмісту вебсторінки і коли видаляється HTML розмітка то відбувається обробка стрічки:

>>> raw = open('document.txt').read()

>>> type(raw)

<type 'str'>

Результати  токенізації список в який входять всі слова з тексту. Нормалізація та сортування цього списку приводить до отримання інших списків:

>>> tokens = nltk.word_tokenize(raw)

>>> type(tokens)

<type 'list'>

>>> words = [w.lower() for w in tokens]

>>> type(words)

<type 'list'>

>>> vocab = sorted(set(words))

>>> type(vocab)

<type 'list'>

Тип об’єкту визначає, які операції можуть бути здійснені з цим об’єктом. Наприклад, можна додавати елементи до списку але не можна до стрічки:

>>> vocab.append('blog')

>>> raw.append('blog')

Traceback (most recent call last):

 File "<stdin>", line 1, in <module>

AttributeError: 'str' object has no attribute 'append'

Стрічки та списки можна поєднувати з іншими стрічками та списками, але не можна поєднувати стрічки зі списками:

>>> query = 'Who knows?'

>>> beatles = ['john', 'paul', 'george', 'ringo']

>>> query + beatles

Traceback (most recent call last):

 File "<stdin>", line 1, in <module>

TypeError: cannot concatenate 'str' and 'list' objects

2. Використання Unicode при обробці текстів

Програми обробки природної мови повинні працювати з різними мовами та з різними наборами символів. Твердження «1 байт = 1 символ» є застарілим і в переважній більшості практичних випадків є хибним. В англомовному світі переважно використовується ASCII кодування символів. В Європі використовується  розширений Latin набір символів, який містить такі символи датської та норвежської, як "ø", угорської - "ő", іспанської та бретонської -"ñ" та "ň" чеської та словацької мов. Розглянемо, як використовується Unicode при обробці текстів, що містять відмінні від ASCII символи.

2.1. Поняття Юнікод (Unicode).

Юнікод, (англ. Unicode) — це промисловий стандарт розроблений, щоб зробити можливим для текстів і символів (графічних знаків) всіх писемних систем світу узгоджене представлення (репрезентацію) і обробку комп’ютерами. Юнікод підтримує більш ніж мільйон символів. Кожному символу ставиться у відповідність число, яке називають кодовою точкою. В Python кодові точки записуються у вигляді \uXXXX  , де XXXX  - чотири символи шістнадцяткового числа.

В межах програми обробка стрічок Unicode відбувається аналогічно до звичайних стрічок. Однак, коли Unicode символи зберігаються у файл або виводяться на екран, вони повинні бути закодовані, як потік байт. Деякі кодування (такі як ASCII та Latin-2) використовують один байт для представлення одної кодової точки і відповідно підтримують невеликий набір символів Unicode, достатній для одної мови. Інші кодування (такі як UTF-8) використовують послідовності байтів і можуть представити весь набір символів Unicode.

Текст у файлах є в певному кодування і потрібен певний механізм для перетворення його до Unicode. Такий механізм називають — декодування. Навпаки записати  Unicode символи у файл або вивести на екран можна тільки попередньо перетворивши їх у потрібне кодування. Таке перетворення називають кодуванням. Рис.2.

Рис.2. Кодування і декодування Unicode.

From a Unicode perspective, characters are abstract entities which can be realized as one or more glyphs. Only glyphs can appear on a screen or be printed on paper. A font is a mapping from characters to glyphs.

2.2. Одержання закодованого тексту з файлів.

Нехай існують невеликі текстові файли відомого кодування. Файл Ukrainian1-Cyrillic (перше речення декларації прав людини)  з текстом українською мовою в кодуванні  Сyrillic та файл polish-lat2.txt  з текстом польською мовою у кодуванні  Latin-2 (ISO-8859-2). За допомогою функції  nltk.data.find() знайдемо місцезнаходження цих файлів:

>>> path = nltk.data.find('corpora/udhr/Ukrainian1-Cyrillic')

>>> path1 = nltk.data.find('corpora/unicode_samples/polish-lat2.txt')

Модуль Python codecs  забезпечує функції читання кодованих даних в Unicode стрічку і запису Unicode стрічки в кодовану форму. Функція codecs.open() потребує параметра кодування файлу для читання чи запису. Перед використанням модуля потрібно його імпортувати і при читанні вказувати тип кодування:

>>> import codecs

>>> f = codecs.open(path, encoding='cyrillic')

>>> f1 = codecs.open(path1, encoding='latin2')

Список параметрів кодування модуля codecs, можна переглянути за адресою http://docs.python.org/lib/standard-encodings.html. Для запису даних у файл потрібно скористатись наступною конструкцією: f = codecs.open(path, 'w', encoding='utf-8').

Текст прочитаний з f буде в Unicode. Для представлення цього тексту на екрані потрібно його закодувати. В Python кодування unicode_escape перетворює всі не ASCII символи в їх  представлення \uXXXX . Кодові точки вище ASCII 0=127 але до 256 представляються у двоцифровій формі \хХХ.

>>> for line in f1:

...     line = line.strip()

...     print line.encode('unicode_escape')

Pruska Biblioteka Pa\u0144stwowa. Jej dawne zbiory znane pod nazw\u0105

"Berlinka" to skarb kultury i sztuki niemieckiej. Przewiezione przez

Niemc\xf3w pod koniec II wojny \u015bwiatowej na Dolny \u015al\u0105sk, zosta\u0142y

odnalezione po 1945 r. na terytorium Polski. Trafi\u0142y do Biblioteki

Jagiello\u0144skiej w Krakowie, obejmuj\u0105 ponad 500 tys. zabytkowych

archiwali\xf3w, m.in. manuskrypty Goethego, Mozarta, Beethovena, Bacha.

В першій стрічці послідовність \u0144, починається з символу \u. Відповідний  Unicode символ буде відображатися на екрані, як ń. В третій стрічці є символ  \xf3, який відповідає ó, оскільки він є з проміжку 128-255.

В Python, Unicode стрічку записують вказавши на початку символ u, ( u'hello' –Юнікод стрічка). Довільний  Unicode символ може бути визначений всередині Unicode стрічки використовуючи представлення \uXXXX . Можна знайти числове значення кодової точки використовуючи функцію ord():

>>> ord('a')

97

>>> ord('а')

224

В шістнадцятковій формі  97 це 0061 а 224 це 00Е0 , що дозволяє представити ці символи відповідними кодовими точками:

>>> a = u'\u0061'

>>> b = u'\u00E0'

>>> a

u'a'

>>> print a

a

>>> b

u'\xe0'

>>> print b

à

2.3. Використання локального кодування в Python

При роботі з символами певного локального кодування, для можливості використання стандартних методів вводу і редагування стрічок у файлі Python потрібно записати стрічку '# -*- coding: <coding> -*-' першим або другим рядком у файлі.  <coding> це стрічка така як  'latin-1', 'big5' or 'utf-8' (Рис.4.).

3. Нормалізація тексту

В попередніх лабораторних роботах перед обробкою тексту всі літери слів перетворювались у малі літери (set(w.lower() for w in text).). Використовуючи lower() текст нормалізується для усунення розбіжностей між  «The»  та «the». Часто потрібно відділити від слів афікси. Така задача називається стемінгом. Для перевірки чи словоформа є словом у словнику потрібно здійснити лематизацію (отримати канонічну форму лексеми):

>>> raw = """DENNIS: Listen, strange women lying in ponds distributing swords

... is no basis for a system of government.  Supreme executive power derives from

... a mandate from the masses, not from some farcical aquatic ceremony."""

>>> tokens = nltk.word_tokenize(raw)

3.1. Стемінг

NLTK містить декілька стандартних програм для здійснення стемінгу. Porter та Lancaster програми здійснюють стемінг (відкидання афіксів) на основі наборів правил. Porter стемер коректно обробляє слово lying (lie), а Lancaster стемер це слово обробляє з помилкою.

>>> porter = nltk.PorterStemmer()

>>> lancaster = nltk.LancasterStemmer()

>>> [porter.stem(t) for t in tokens]

['DENNI', ':', 'Listen', ',', 'strang', 'women', 'lie', 'in', 'pond',

'distribut', 'sword', 'is', 'no', 'basi', 'for', 'a', 'system', 'of', 'govern',

'.', 'Suprem', 'execut', 'power', 'deriv', 'from', 'a', 'mandat', 'from',

'the', 'mass', ',', 'not', 'from', 'some', 'farcic', 'aquat', 'ceremoni', '.']

>>> [lancaster.stem(t) for t in tokens]

['den', ':', 'list', ',', 'strange', 'wom', 'lying', 'in', 'pond', 'distribut',

'sword', 'is', 'no', 'bas', 'for', 'a', 'system', 'of', 'govern', '.', 'suprem',

'execut', 'pow', 'der', 'from', 'a', 'mand', 'from', 'the', 'mass', ',', 'not',

'from', 'som', 'farc', 'aqu', 'ceremony', '.']

Результати стемінгу не є однозначними і тому стемер вибирається той, який дає кращі результати для визначеної задачі. Porter стемер найкраще використовувати для індексування деякого тексту для підтримки пошукових операцій (забезпечення пошуку всіх форм слова). Порівняйте результати побудови конкордансу для слова “lie”, без індексування та з попереднім індексуванням (class IndexedText(object)).

 

class IndexedText(object):

   def __init__(self, stemmer, text):

       self._text = text

       self._stemmer = stemmer

       self._index = nltk.Index((self._stem(word), i)

                                for (i, word) in enumerate(text))

   def concordance(self, word, width=40):

       key = self._stem(word)

       wc = width/4                # words of context

       for i in self._index[key]:

           lcontext = ' '.join(self._text[i-wc:i])

           rcontext = ' '.join(self._text[i:i+wc])

           ldisplay = '%*s'  % (width, lcontext[-width:])

           rdisplay = '%-*s' % (width, rcontext[:width])

           print ldisplay, rdisplay

   def _stem(self, word):

       return self._stemmer.stem(word).lower()

>>> porter = nltk.PorterStemmer()

>>> grail = nltk.corpus.webtext.words('grail.txt')

>>> text = IndexedText(porter, grail)

>>> text.concordance('lie')

r king ! DENNIS : Listen , strange women lying in ponds distributing swords is no

beat a very brave retreat . ROBIN : All lies ! MINSTREL : [ singing ] Bravest of

      Nay . Nay . Come . Come . You may lie here . Oh , but you are wounded !

doctors immediately ! No , no , please ! Lie down . [ clap clap ] PIGLET : Well

ere is much danger , for beyond the cave lies the Gorge of Eternal Peril , which

  you . Oh ... TIM : To the north there lies a cave -- the cave of Caerbannog --

h it and lived ! Bones of full fifty men lie strewn about its lair . So , brave k

not stop our fight ' til each one of you lies dead , and the Holy Grail returns t

>>> grail = nltk.Text(nltk.corpus.webtext.words('grail.txt'))

>>> grail.concordance('lie')

      Nay . Nay . Come . Come . You may lie here . Oh , but you are wounded !

doctors immediately ! No , no , please ! Lie down . [ clap clap ] PIGLET : Well

h it and lived ! Bones of full fifty men lie strewn about its lair . So , brave k

3.2. Лематизація.

WordNet лематизатор видаляє афікси тільки якщо слово, яке отримується в процесі лематизації є в його словнику. Ця процедура робить лематизацію повільнішою за стемінг. Слово lying оброблено з помилкою, але слово women перетворено у woman.

>>> wnl = nltk.WordNetLemmatizer()

>>> [wnl.lemmatize(t) for t in tokens]

['DENNIS', ':', 'Listen', ',', 'strange', 'woman', 'lying', 'in', 'pond',

'distributing', 'sword', 'is', 'no', 'basis', 'for', 'a', 'system', 'of',

'government', '.', 'Supreme', 'executive', 'power', 'derives', 'from', 'a',

'mandate', 'from', 'the', 'mass', ',', 'not', 'from', 'some', 'farcical',

'aquatic', 'ceremony', '.']

WordNet лематизатор можна використовувати для побудови словника деякого тексту. В результаті можна отримати список лем.

4. Сегментація

Токенізація це найбільш загальний випадок сегментації.

4.1. Сегментація тексту на окремі речення

Робота з текстами на рівні окремих слів часто передбачає можливість поділу тексту на окремі речення. Деякі корпуси забезпечують можливість доступу на рівні окремих речень. В наступному прикладі визначається середня довжина речення в корпусі Brown:

>>> len(nltk.corpus.brown.words()) / len(nltk.corpus.brown.sents())

20.250994070456922

У випадку якщо текст представлений, як послідовність символів, то перед токенізацією необхідно поділити текст на окремі речення. NLTK забезпечує таку можливість за допомогою програми Punkt сегментації тексту на речення. У наступному прикладі показано використання цієї програми:

>>> sent_tokenizer=nltk.data.load('tokenizers/punkt/english.pickle')

>>> text = nltk.corpus.gutenberg.raw('chesterton-thursday.txt')

>>> sents = sent_tokenizer.tokenize(text)

>>> pprint.pprint(sents[171:181])

['"Nonsense!',

'" said Gregory, who was very rational when anyone else\nattempted paradox.',

'"Why do all the clerks and navvies in the\nrailway trains look so sad and tired,...',

'I will\ntell you.',

'It is because they know that the train is going right.',

'It\nis because they know that whatever place they have taken a ticket\nfor that ...',

'It is because after they have\npassed Sloane Square they know that the next stat...',

'Oh, their wild rapture!',

'oh,\ntheir eyes like stars and their souls again in Eden, if the next\nstation w...'

'"\n\n"It is you who are unpoetical," replied the poet Syme.']

Зауважимо, що цей приклад це одне речення, повідомлення про промову Mr Lucian Gregory. Промова містить декілька речень і доцільно їх виділити, як окремі стрічки.

Сегментація тексту на речення є складною процедурою, оскільки навіть такий явний розділовий знак межі речення, як крапка, може використовуватись у скороченнях, абревіатурах та їх комбінаціях.

4.2. Сегментація тексту на окремі слова

Для деяких писемностей токенізація тексту є складною процедурою оскільки складно встановити межі слова. Наприклад три символи стрічки китайською 爱国人 (ai4 "love" (verb), guo3 "country", ren2 "person") можуть бути поділені і як爱国 / , "country-loving person" і як / 国人, "love country-person."

Подібна проблема виникає при обробці усного мовлення, коли слухач змушений сегментувати безперервний потік звуків на окремі слова. Особливо складно це зробити, якщо слова є попередньо невідомі (при вивченні мови або якщо немовля сприймає мову батьків). Розглянемо наступний приклад в якому видалені межі слів:

(1)

a.

doyouseethekitty

b.

seethedoggy

c.

doyoulikethekitty

d.

likethedoggy

Спочатку потрібно описати задачу: потрібно знайти спосіб відділити текст від власне сегментації. Цього можна досягнути промарнувавши кожен символ булевим значенням, яке буде вказувати, що після символу йде межа слова. Подібний результат може отримати учень на слух сприймаючи паузи при вимові. Результат представимо наступним чином. seg1  – початкова сегментація, seg2 - результуюча сегментація:

>>> text = "doyouseethekittyseethedoggydoyoulikethekittylikethedoggy"

>>> seg1 = "0000000000000001000000000010000000000000000100000000000"

>>> seg2 = "0100100100100001001001000010100100010010000100010010000"

Стрічки сегментації містять нулі та одиниці та їх довжина менша на один символ від початкового тексту (текст довжиною N елементів може мати тільки N-1 місць розділу). Функція segment() в наступному прикладі дозволяє отримати оригінальний сегментований текст на основі поданого вище представлення.

 

def segment(text, segs):

   words = []

   last = 0

   for i in range(len(segs)):

       if segs[i] == '1':

           words.append(text[last:i+1])

           last = i+1

   words.append(text[last:])

   return words

>>> text = "doyouseethekittyseethedoggydoyoulikethekittylikethedoggy"

>>> seg1 = "0000000000000001000000000010000000000000000100000000000"

>>> seg2 = "0100100100100001001001000010100100010010000100010010000"

>>> segment(text, seg1)

['doyouseethekitty', 'seethedoggy', 'doyoulikethekitty', 'likethedoggy']

>>> segment(text, seg2)

['do', 'you', 'see', 'the', 'kitty', 'see', 'the', 'doggy', 'do', 'you',

'like', 'the', kitty', 'like', 'the', 'doggy']

Тепер задачу сегментації можна розглядати як пошукову задачу: знайти стрічку бітів, яка приводить до коректної сегментації стрічки тексту на слова. Учень запам’ятовує слова і зберігає їх у словнику. Маючи відповідний словник, можливо здійснити реконструкцію початкового тексту, як послідовність лексичних одиниць. Побудуємо цільову функцію, значення якої буде оптимізоване на основі розміру словника та розміру інформації необхідної для реконструкції початкового тексту зі словника Рис.3..

Рис.3. Визначення цільової функції:

На основі гіпотетично сегментованого початкового тексту(ліва колонка ) отримуємо словник та таблицю (середня колонка), які забезпечують реконструкцію початкового тексту. Загальна кількість символів у лексиконі (з врахуванням символу границі слова) та сума елементів в таблиці служать числовим значенням для оцінки якості сегментації (права колонка). Менше, за знайдене, значення вказує на кращий варіант сегментації.

Для розрахунку цієї цільової функції можна використати наступну функцію:

 

def evaluate(text, segs):

   words = segment(text, segs)

   text_size = len(words)

   lexicon_size = len(' '.join(list(set(words))))

   return text_size + lexicon_size

>>> text = "doyouseethekittyseethedoggydoyoulikethekittylikethedoggy"

>>> seg1 = "0000000000000001000000000010000000000000000100000000000"

>>> seg2 = "0100100100100001001001000010100100010010000100010010000"

>>> seg3 = "0000100100000011001000000110000100010000001100010000001"

>>> segment(text, seg3)

['doyou', 'see', 'thekitt', 'y', 'see', 'thedogg', 'y', 'doyou', 'like',

'thekitt', 'y', 'like', 'thedogg', 'y']

>>> evaluate(text, seg3)

46

>>> evaluate(text, seg2)

47

>>> evaluate(text, seg1)

63

Останній крок це власне пошук послідовності нулів та одиниць, яка максимізує цю цільову функцію. Потрібно зазначити, що найкращий варіант сегментації містить «слово» thekitty, оскільки недостатньо даних для подальшої сегментації.

 

from random import randint

def flip(segs, pos):

   return segs[:pos] + str(1-int(segs[pos])) + segs[pos+1:]

def flip_n(segs, n):

   for i in range(n):

       segs = flip(segs, randint(0,len(segs)-1))

   return segs

def anneal(text, segs, iterations, cooling_rate):

   temperature = float(len(segs))

   while temperature > 0.5:

       best_segs, best = segs, evaluate(text, segs)

       for i in range(iterations):

           guess = flip_n(segs, int(round(temperature)))

           score = evaluate(text, guess)

           if score < best:

               best, best_segs = score, guess

       score, segs = best, best_segs

       temperature = temperature / cooling_rate

       print evaluate(text, segs), segment(text, segs)

   print

   return segs

>>> text = "doyouseethekittyseethedoggydoyoulikethekittylikethedoggy"

>>> seg1 = "0000000000000001000000000010000000000000000100000000000"

>>> anneal(text, seg1, 5000, 1.2)

60 ['doyouseetheki', 'tty', 'see', 'thedoggy', 'doyouliketh', 'ekittylike', 'thedoggy']

58 ['doy', 'ouseetheki', 'ttysee', 'thedoggy', 'doy', 'o', 'ulikethekittylike', 'thedoggy']

56 ['doyou', 'seetheki', 'ttysee', 'thedoggy', 'doyou', 'liketh', 'ekittylike', 'thedoggy']

54 ['doyou', 'seethekit', 'tysee', 'thedoggy', 'doyou', 'likethekittylike', 'thedoggy']

53 ['doyou', 'seethekit', 'tysee', 'thedoggy', 'doyou', 'like', 'thekitty', 'like', 'thedoggy']

51 ['doyou', 'seethekittysee', 'thedoggy', 'doyou', 'like', 'thekitty', 'like', 'thedoggy']

42 ['doyou', 'see', 'thekitty', 'see', 'thedoggy', 'doyou', 'like', 'thekitty', 'like', 'thedoggy']

'0000100100000001001000000010000100010000000100010000000'

Останній крок це власне пошук послідовності нулів та одиниць, яка максимізує цю цільову функцію. Потрібно зазначити, що найкращий варіант сегментації містить «слово» thekitty, оскільки недостатньо даних для подальшої сегментації.

5. Форматування

5.1. Стрічки і форматування

Відомі два шляхи вивести на екран вміст об’єктів:

>>> word = 'cat'

>>> sentence = """hello

... world"""

>>> print word

cat

>>> print sentence

hello

world

>>> word

'cat'

>>> sentence

'hello\nworld'

Команда print дозволяє отримати найбільш придатне, для читання, представлення об’єкту. Другий спосіб — ввести назву змінної в командному рядку — показує стрічку, яка може бути використана для оновлення цього об’єкту. Важливо зрозуміти, ці два результати це стрічки, виведені на екран для користувача і не дають ніякої інформації про фактичне внутрішнє представлення об’єкта.

Існують інші шляхи для виведення на екран об’єкту, як стрічки символів. Вони можуть також використовуватися і для експортування даних у файл певного формату, який буде використаний зовнішньою програмою.

Форматовані вихідні дані звичайно містять комбінацію змінних та наперед визначених стрічок. Наприклад результати частотного розподілу можна представити як:

>>> fdist = nltk.FreqDist(['dog', 'cat', 'dog', 'cat', 'dog', 'snake', 'dog', 'cat'])

>>> for word in fdist:

...     print word, '->', fdist[word], ';',

dog -> 4 ; cat -> 3 ; snake -> 1 ;

Уникнути небажаних пробілів та покращити читабельність програми дозволяє використання виразів форматування.

>>> for word in fdist:

...    print '%s->%d;' % (word, fdist[word]),

dog->4; cat->3; snake->1;

Тестування стрічки, яка містить вираз форматування дозволяє глибше зрозуміти механізм форматованого виводу.

>>> '%s->%d;' % ('cat', 3)

'cat->3;'

>>> '%s->%d;' % 'cat'

Traceback (most recent call last):

 File "<stdin>", line 1, in <module>

TypeError: not enough arguments for format string

Спеціальні символи %s та %d вказують на тимчасові місця (позиції) для стрічок та цілих (десяткових чисел). Ці символи записуються всередині стрічки і використовується оператор % для їх комбінування, подібно до наступного прикладу:

>>> '%s->' % 'cat'

'cat->'

>>> '%d' % 3

'3'

>>> 'I want a %s right now' % 'coffee'

'I want a coffee right now'

У виразі можуть бути багато тимчасових позицій але після оператора  %  потрібно визначити кортеж з такою самою кількістю значень.

>>> "%s wants a %s %s" % ("Lee", "sandwich", "for lunch")

'Lee wants a sandwich for lunch'

Значення для тимчасових позицій можна вказувати не безпосередньо, а наприклад так як в зроблено у наступному циклі:

>>> template = 'Lee wants a %s right now'

>>> menu = ['sandwich', 'spam fritter', 'pancake']

>>> for snack in menu:

...     print template % snack

...

Lee wants a sandwich right now

Lee wants a spam fritter right now

Lee wants a pancake right now

Символи  %s та %d називають специфікаторами формату. Вони починаються з символу % і завершуються символом таким як  s (для стрічки) чи d (для цілих чисел). Стрічка, яка містить специфікатори формату називають стрічкою форматування. Поєднання стрічки форматування з оператором % та кортежем значень утворює стрічку виразу форматування.

Стрічка форматування виводить вихідні дані на екран або на сторінку довільної ширини такої як %s та %d. Можна визначити ширину як %6s, що дозволить отримати стрічку доповнену пробілами до ширини 6 символів. Значення змінної буде вирівняне по правому краю, а у випадку використання символу «мінус » - по лівому краю. У випадку, коли наперед невідомо, якої ширини може бути змінна в стрічці форматування використовується зірочка, яка потім визначається за допомогою окремої змінної.

>>> '%6s' % 'dog'

'   dog'

>>> '%-6s' % 'dog'

'dog   '

>>> width = 6

>>> '%-*s' % (width, 'dog')

'dog   '

>>> '%*s' % (15, "Monty Python")

'   Monty Python'

Інший спосіб контролю символів використовується для цілих чисел та чисел з плаваючою крапкою. Оскільки символ % має спеціальне значення в стрічці форматування то при необхідності використати цей символ у вихідних даних потрібно додати перед ним ще один символ % .

>>> count, total = 3205, 9375

>>> "accuracy for %d words: %2.4f%%" % (total, 100 * count / total)

'accuracy for 9375 words: 34.1867%'

Для представлення даних у вигляді таблиці також необхідно використовувати стрічки форматування. В наступному прикладі показано, яким чином працює функція представлення у вигляді таблиці результатів умовного частотного розподілу.

 

def tabulate(cfdist, words, categories):

   print '%-16s' % 'Category',

   for word in words:                                  # column headings

       print '%6s' % word,

   print

   for category in categories:

       print '%-16s' % category,                       # row heading

       for word in words:                              # for each word

           print '%6d' % cfdist[category][word],       # print table cell

       print                                           # end the row

>>> from nltk.corpus import brown

>>> cfd = nltk.ConditionalFreqDist(

...           (genre, word)

...           for genre in brown.categories()

...           for word in brown.words(categories=genre))

>>> genres = ['news', 'religion', 'hobbies', 'science_fiction', 'romance', 'humor']

>>> modals = ['can', 'could', 'may', 'might', 'must', 'will']

>>> tabulate(cfd, modals, genres)

Category            can  could    may  might   must   will

news                 93     86     66     38     50    389

religion             82     59     78     12     54     71

hobbies             268     58    131     22     83    264

science_fiction      16     49      4     12      8     16

romance              74    193     11     51     45     43

humor                16     30      8      8      9     13

Використовуючи вираз width = max(len(w) for w in words) можна автоматично налаштувати ширину колонки, а кома в кінці операторів  print  не дозволяє колонкам перекриватися між собою.

5.2. Запис результатів у файл

Наступний приклад показує, яким чином відкрити файл output.txt для запису, та зберегти в ньому результати роботи програми.

>>> output_file = open('output.txt', 'w')

>>> words = set(nltk.corpus.genesis.words('english-kjv.txt'))

>>> for word in sorted(words):

...     output_file.write(word + "\n")

Виконати самостійно:

Перевірити навіщо перед записом у файл до кожного рядка додається символ  \n . Спробуйте також використати  word + "\r\n" вираз. Що станеться, якщо опустити ці символи output_file.write(word)?

При записі у файл не текстових даних їх попередньо потрібно перетворити у стрічку. Перетворення можна зробити використавши стрічку форматування, як було показано вище або зробити перетворення наступним чином:

>>> len(words)

2789

>>> str(len(words))

'2789'

>>> output_file.write(str(len(words)) + "\n")

>>> output_file.close()

Текстові вихідні дані часто корисно обробити для покращення їх відображення. Розглянемо наступний приклад зі складним виглядом оператора print:

>>> saying = ['After', 'all', 'is', 'said', 'and', 'done', ',',

...           'more', 'is', 'said', 'than', 'done', '.']

>>> for word in saying:

...     print word, '(' + str(len(word)) + '),',

After (5), all (3), is (2), said (4), and (3), done (4), , (1), more (4), is (2), said (4), than (4), done (4), . (1),

Аналогічний результат, але з фіксованою довжиною рядка можна отримати з використанням модуля textwrap :

>>> from textwrap import fill

>>> format = '%s (%d),'

>>> pieces = [format % (word, len(word)) for word in saying]

>>> output = ' '.join(pieces)

>>> wrapped = fill(output)

>>> print wrapped

After (5), all (3), is (2), said (4), and (3), done (4), , (1), more

(4), is (2), said (4), than (4), done (4), . (1),

Додаток А

Сьогодні ми вивчили:

from __future__ import division

Імпортування модуля для роботи з числами з плаваючою крапкою

urlopen(url).read()

Функція відкривання та читання файла за адресою url

nltk.word_tokenize(raw)

Токенізація тексту raw

nltk.Text(tokens)

Перетворення тексту tokens в NLTK текст

raw.find

Знайти стрічку в raw

raw.rfind

Знайти стрічку в raw. Пошук здійснювати з кінця.

nltk.clean_html(html)

Очистити текст від html розмітки.

open('document.txt')

Відкрити файл

f.read()

Прочитати файл

os.listdir('.')

Встановити вміст директорії

line.strip()

Обрізати стрічку по останньому символу

nltk.data.find('corpora/gutenberg/melville-moby_dick.txt')

Знайти місцезнаходження файлу

open(path, 'rU').read()

Відкрити файл за вказаним шляхом для читання і прочитати його. Різні способи маркування нового рядка ігноруються

raw_input("Enter some text: ")

Ввести текст з клавіатури

codecs.open(path1, encoding='latin2')

ord('a')

line.encode('unicode_escape')

nltk.PorterStemmer()

Модуль Porter стемера

nltk.LancasterStemmer()

Модуль Lancaster стемера

nltk.WordNetLemmatizer()

Модуль WordNet лематизатора

nltk.data.load('tokenizers/punkt/english.pickle')

sent_tokenizer.tokenize(text)

Сегментувати текст на окремі речення

open('output.txt', 'w')

Відкрити файл для запису

output_file.write(word + "\n")

Записати у файл word та символ початку нового рядка

Порядок виконання роботи

1. Ознайомитися з теоретичними відомостями.

2. Виконати приклади, які використовуються в теоретичних відомостях.

3. Виконати наступні вправи.

  1.  Напишіть функцію, яка приймає адресу URL, як аргумент, і повертає те що міститься за цією адресою з видаленням HTML розмітки. Використовувати urllib.urlopen для доступу до контенту наступним чином raw_contents = urllib.urlopen('http://www.nltk.org/').read().
  2.  Збережіть деякий текст у файлі corpus.txt. Визначити функцію load(f) для читання файлу, назва якого є її аргументом і повертає стрічку, яка містить текст з файлу.
  3.  Перепишіть наступний цикл як list comprehension:
  1.  

>>> sent = ['The', 'dog', 'gave', 'John', 'the', 'newspaper']

>>> result = []

>>> for word in sent:

...     word_len = (word, len(word))

...     result.append(word_len)

>>> result

[('The', 3), ('dog', 3), ('gave', 4), ('John', 4), ('the', 3), ('newspaper', 9)]

  1.  Перевірити різницю між стрічками і цілим виконавши наступні дії: "3" * 7 та 3 * 7. Спробуйте здійснити конвертування між стрічками і цілими використавши int("3") та str(3).
  2.  Що станеться, коли стрічки форматування %6s та %-6s використовується для відображення стрічки довшої ніж 6 символів?
  3.  Прочитайте деякий текст з корпуса, здійсніть його токенізацію і збережіть у список всі wh-слова, які в ньому зустрічаються.
  4.  Створіть файл, який буде містити слова та їх частоту записані в окремих рядках через пробіл ( fuzzy 53). Прочитайте цей файл використовуючи open(filename).readlines().  Розділіть кожну стрічку на дві частини використовуючи split(), і перетворіть число в ціле значення використовуючи int(). Результат повинен бути у вигляді списку: [['fuzzy', 53], ...].
  5.  Напишіть програму доступу до вебсторінки і вилучення з неї деякого тексту.
  6.  З тексту мовою, яка має гармонію голосних ( Hungarian), вилучіть у словах послідовності голосних і створіть частотну таблицю біграмів голосних.
  7.  Модуль random включає функцію choice(), яка випадковим чином вибирає елементи послідовності. Наприклад, choice("aehh ") буде вибирати один з чотирьох символів. Напишіть програму генерації стрічки з 500 випадково вибраних символів "aehh ". Для поєднання елементів в стрічку використовуйте ''.join() . Нормалізуйте отриманий результат використовуючи split() та join().
  8.  Здійсніть аналіз числового виразу в наступному реченні з корпуса MedLine: The corresponding free cortisol fractions in these sera were 4.53 +/- 0.15% and 8.16 +/- 0.23%, respectively. Чи можна сказати, що 4.53 +/- 0.15% це три окремих слова?  Чи це одне складне слово? Чи це дев’ять слів "four point five three, plus or minus fifteen percent"? Чи це взагалі не можна вважати словом? При вирішенні яких задач потрібно вибирати ту чи іншу відповідь?
  9.  Міра оцінки читабельності використовується для оцінки складності тексту для читання. Нехай, μw - середня кількість літер у слові, та μs – середнє значення кількості слів у реченні в певному тексті. Automated Readability Index (ARI) тексту визначається згідно виразу: 4.71 μw + 0.5 μs - 21.43. Визначити значення ARI для різних частин корпуса Brown Corpus, включаючи частину f (popular lore) та j (learned). Використовуйте nltk.corpus.brown.words() для знаходження послідовності слів та nltk.corpus.brown.sents() для знаходження послідовності речень.
  10.  Використовуючи Porter стемер нормалізуйте будь-який токенізований текст . До того самого тексту застосуйте Lancaster стемер. Результати порівняйте та поясніть.
  11.  Доступіться до текстів ABC Rural News та ABC Science News з корпуса (nltk.corpus.abc). Знайдіть значення для оцінки читабельності текстів (аналогічно до задачі №12). Використовуйте Punkt для поділу тексту на окремі речення.
  12.  Перепишіть наступний цикл, як list comprehension:
  1.  

>>> words = ['attribution', 'confabulation', 'elocution',

...          'sequoia', 'tenacious', 'unidirectional']

>>> vsequences = set()

>>> for word in words:

...     vowels = []

...     for char in word:

...         if char in 'aeiou':

...             vowels.append(char)

...     vsequences.add(''.join(vowels))

>>> sorted(vsequences)

['aiuio', 'eaiou', 'eouio', 'euoia', 'oauaio', 'uiieioa']

4. Підготувати і оформити звіт.

Варіанти завдань

Варіант

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

Номери завдань

1

1

1

1

1

1

1

1

1

1

1

1

1

1

1

2

2

2

2

2

2

2

2

2

2

2

2

2

2

2

3

3

3

3

3

3

3

3

3

3

3

3

3

3

3

4

4

4

4

4

4

4

4

4

4

4

4

4

4

4

5

5

5

5

5

5

5

5

5

5

5

5

5

5

5

7

7

7

7

7

7

7

7

7

7

7

7

7

7

7

8

6

13

11

8

6

13

11

8

6

13

8

6

13

11

9

10

12

9

10

12

9

10

12

9

10

12

9

10

12

14

15

14

15

14

15

14

15

14

15

14

15

14

15

14

Варіант

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

Номери завдань

1

1

1

1

1

1

1

1

1

1

1

1

1

1

1

2

2

2

2

2

2

2

2

2

2

2

2

2

2

2

3

3

3

3

3

3

3

3

3

3

3

3

3

3

3

4

4

4

4

4

4

4

4

4

4

4

4

4

4

4

5

5

5

5

5

5

5

5

5

5

5

5

5

5

5

7

7

7

7

7

7

7

7

7

7

7

7

7

7

7

13

8

6

11

13

8

6

11

13

8

6

13

8

6

11

9

10

12

9

10

12

9

10

12

9

10

12

9

10

12

14

15

14

15

14

15

14

15

14

15

14

15

14

15

15

Зміст звіту

  1.  Титульний аркуш.
  2.  Мета роботи.
  3.  Короткі теоретичні відомості.
  4.  Тексти програм на мові Python.
  5.  Висновок.

Література

  1.  Steven Bird, Ewan Klein, Edward Loper Introduction to Natural Language Processing. 2001-2007 University of Pennsylvania.
  2.  Г. Россум, Ф.Л.Дж. Дрейк, Д.С. Откидач, М. Задка, М. Левис, С.Монтаро, Э.С.Реймонд, А.М.Кучлинг, М.-А.Лембург, К.-П.Йи, Д.Ксиллаг, Х.ГПетрилли, Б.А.Варсав, Дж.К.Ахлстром, Дж.Рокинд, Н.Шеменон, С.Мулендер. Язык программирования Python./ 2001 – 452c.
  3.  Сузи Р. А. Язык программирования Python.- 206с.
  4.  David Mertz Text Processing in Python Addison WesleyBiber, 2003 - 544.

Інтернет посилання

  1.  http://www.nltk.org
  2.  http://python.org


 

А также другие работы, которые могут Вас заинтересовать

39871. 40 квартирный жилой дом 5.52 MB
  Для защиты деревянных элементов от возгорания и биологического разрушения обработать их препаратом БОПОД. В каждой квартире установлен газовый котел АльфаКолор работающий на природном газу. Определяем расчетный пролет перемычки: Элемент перемычки работает как однопролетная свободно лежащая равномерно загруженная балка. Плита монолитно связана со ступенями которые армируют по конструктивным соображениям и её несущая способность с учетом работы ступеней вполне обеспечивается.
39872. Разработка эффективной технологии сушки рециклового винилхлорида 1.66 MB
  Наибольший интерес к винилхлориду проявили позднее когда И. Первое промышленное производство винилхлорида основанное на щелочной обработке дихлорэтана изза недостатков не позволили полностью удовлетворить растущие потребности в винилхлориде. Простота и удобство этой реакции позволили за очень короткое время построить первые заводы сначала в Германии а затем в Англии. В настоящее время основным видом сырья для производства винилхлорида традиционно используют этилен ацетилен смеси этилена с ацетиленом получаемые крекингом нафты или...
39873. Производство глицерина производительностью 40000 т/год 331.5 KB
  Это позволило ориентировать нефтигазопереработку на обеспечение народного хозяйства не только топливом маслами и другими товарными продуктами но и дешёвым сырьём для химической и нефтехимической отраслей промышленности производящих различные синтетические продукты: пластические массы синтетические каучуки химические волокна спирты синтетические масла и др. Позже в 1913 году немецким ученым Гейнеманом предпринимались попытки синтезировать глицерин путем омыления 123трихлорпропана получаемого прямым хлорированием пропилена: C12...
39874. Усовершенствование технологии получения глицерина производительностью 40000 т/год 647 KB
  В разделе Автоматизация для контроля выбраны параметры которые позволяют наиболее полно и своевременно контролировать и регулировать ход процесса. Это позволило ориентировать нефтигазопереработку на обеспечение народного хозяйства не только топливом маслами и другими товарными продуктами но и дешёвым сырьём для химической и нефтехимической отраслей промышленности производящих различные синтетические продукты: пластические массы синтетические каучуки химические волокна спирты синтетические масла и др. Позже в 1913 году немецким ученым...
39875. Разработка технологии очистки отходящих газов содовых производств от токсичных компонентов 392 KB
  Одним из перспективных направлений природоохранной деятельности по защите воздушного бассейна от губительного воздействия вредных токсичных веществ содержащихся в отходящих промышленных газах является метод каталитического окисления. Получение кальцинированной соды включает следующие основные стадии: приготовление аммонизированного рассола станция абсорбции; карбонизация аммонизированного рассола с образованием бикарбоната натрия станция карбонизации; отделение бикарбоната натрия от маточника станция фильтрации; очистка и...
39876. Разработка термокаталитического метода обезвреживания отходящих газов цеха абсорбции-дистилляции-карбонизации №3 от токсичных компонентов 1.49 MB
  Одним из перспективных направлений природоохранной деятельности по защите воздушного бассейна от губительного воздействия вредных токсичных веществ содержащихся в отходящих промышленных газах является метод каталитического окисления.3 Источники образования газообразных выбросов производства цеха абсорбциидистилляциикарбонизации №3 На производстве кальцинированной соды к газообразным выбросам относятся: газовые выбросы после промывателя газа колоннII воздух после промывателя воздуха фильтров организованные выбросы после сборника...
39878. ОТЧЕТ по преддипломной производственной практике на ЗАО “Каустик” ЦЕХ № 21 ПРОИЗВОДСТВО ПЕРХЛОРВИНИЛОВОЙ СМОЛЫ 471.5 KB
  Добавление к ЧХУ 3 дихлорбензола позволяет значительно сократить время хлорирования. Из цистерны поливинилхлорид транспортируется по трубопроводу сжатым воздухом давлением 0305 МПа в расходные бункеры поз. 2814 и в силосы поз. Из силосов поливинилхлорид транспортируется по трубопроводу сжатым воздухом давлением 0305 МПа в расходные бункеры поз.
39879. Проверка двигателя на перегрузочную способность и нагрев 483.5 KB
  В задании предполагается, что после отключения двигатель охлаждается до температуры окружающей среды. Время работы не превышает 90 мин, за которое двигатель не достигнет установившейся температуры. Следовательно, в задании имеет место кратковременный режим работы электродвигателя S2.