AI/ fit_pipeline.ipynb
2022-08-28 11:16:54 +03:00

1179 lines
122 KiB
Plaintext
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

{
"cells": [
{
"cell_type": "code",
"execution_count": 1,
"id": "10e636e2-5f38-43cb-adc6-b2f928d61136",
"metadata": {},
"outputs": [
{
"name": "stderr",
"output_type": "stream",
"text": [
"/home/ubuntu/venv/lib/python3.8/site-packages/tqdm/auto.py:22: TqdmWarning: IProgress not found. Please update jupyter and ipywidgets. See https://ipywidgets.readthedocs.io/en/stable/user_install.html\n",
" from .autonotebook import tqdm as notebook_tqdm\n"
]
}
],
"source": [
"import torch\n",
"import numpy as np\n",
"from transformers import AutoTokenizer, AutoModel\n",
"from tqdm import tqdm\n",
"tqdm.pandas()\n",
"\n",
"import matplotlib.pyplot as plt\n",
"import seaborn as sns\n",
"sns.set()\n",
"import numpy as np\n",
"\n",
"import pandas as pd\n",
"import docx\n",
"import os\n",
"import re\n",
"\n",
"device = 'cuda'"
]
},
{
"cell_type": "code",
"execution_count": 2,
"id": "19c1e5b6-30d7-4684-87be-2777cc14006c",
"metadata": {},
"outputs": [],
"source": [
"#word preprocessing functions\n",
"\n",
"import nltk\n",
"from nltk.tokenize import word_tokenize\n",
"\n",
"from nltk.corpus import stopwords\n",
"from nltk.stem import SnowballStemmer\n",
"from nltk.tokenize import word_tokenize\n",
"\n",
"russian_stopwords = stopwords.words(\"russian\")\n",
"\n",
"russian_stopwords.append('российской')\n",
"russian_stopwords.append('федерации')\n",
"russian_stopwords.append('федерального')\n",
"russian_stopwords.append('настоящих')\n",
"russian_stopwords.append('соответствии')\n",
"russian_stopwords.append('также')\n",
"russian_stopwords.append('рф')\n",
"russian_stopwords.append('ред')\n",
"\n",
"russian_stopwords.append('субсидии')\n",
"russian_stopwords.append('предоставления')\n",
"\n",
"\n",
"def lowercase(text):\n",
" return str(text).lower()\n",
"\n",
"def clean_symb(text):\n",
" return re.sub(r'[^\\w]', ' ', text)\n",
"\n",
"def clear_token(text):\n",
" return word_tokenize(text)\n",
"\n",
"def clean_stopwords(token):\n",
" return ' '.join([i for i in token.split(' ') if i not in russian_stopwords])\n",
"\n",
"def clean_stem(token):\n",
" return [st.stem(i) for i in token]\n",
"\n",
"### combo 3 prev\n",
"def make_clean(s):\n",
" return ' '.join(clean_stem(clean_stopwords(clear_token(s))))"
]
},
{
"cell_type": "code",
"execution_count": 3,
"id": "193b640f-d312-440c-9c89-5cb868132e2c",
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"162"
]
},
"execution_count": 3,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"#find all docs\n",
"\n",
"data_path = './data/Документы/'\n",
"documents = os.listdir(data_path)\n",
"documents = [data_path+d for d in documents]\n",
"len(documents)"
]
},
{
"cell_type": "code",
"execution_count": 4,
"id": "f8dfdf00-ef42-411c-b629-a1fb349c5c94",
"metadata": {},
"outputs": [],
"source": [
"#load and parse doc functions\n",
"\n",
"from nltk.corpus import stopwords\n",
"from nltk.stem import SnowballStemmer\n",
"from nltk.tokenize import word_tokenize\n",
"\n",
"\n",
"def get_text(filename):\n",
" doc = docx.Document(filename)\n",
" fullText = ''\n",
" for para in doc.paragraphs:\n",
" for run in para.runs:\n",
" fullText+=run.text\n",
" fullText+='\\n'\n",
" return fullText\n",
"\n",
"def split_text(text):\n",
" texts, groups = [],[]\n",
" regt = re.findall(r\"{(.*?)}(.*?){(.*?)}\",text.replace('\\n',''))\n",
" for t in regt:\n",
" if t[0]==t[-1]:\n",
" texts.append(t[1])\n",
" groups.append(int(t[0]))\n",
" else:\n",
" print(t)\n",
" \n",
" return texts, groups"
]
},
{
"cell_type": "code",
"execution_count": 5,
"id": "8fdc799a-6ee7-4188-9c70-39b0c11a5833",
"metadata": {
"collapsed": true,
"jupyter": {
"outputs_hidden": true
},
"tags": []
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"('36', '42. ', '37')\n",
"('37', ' (в ред. Правительства РФ от 04.05.2021 N 699) 43. ', '38')\n",
"('38', ' 48.', '7')\n",
"('10', '6. ', '24')\n",
"('24', ' 7. ', '11')\n",
"('11', '8. ', '10')\n",
"('13', 'м) ', '10')\n",
"('10', '(пп. \"о\" в ред. Правительства РФ от 16.08.2021 N 1337)9. ', '13')\n",
"('13', '(в ред. Правительства РФ от 16.08.2021 N 1337)12. ', '11')\n",
"('11', ' ', '24')\n",
"('24', ' ', '17')\n",
"('17', '14. ', '21')\n",
"('21', '15. ', '15')\n",
"('15', '(в ред. Правительства РФ от 16.08.2021 N 1337)16. ', '22')\n",
"('22', ' 17. ', '21')\n",
"('21', '18. ', '28')\n",
"('28', ' ', '12')\n",
"('12', ' ', '30')\n",
"('28', '', '30')\n",
"('30', 'ж) утратил силу. - Правительства РФ от 16.08.2021 N 1337.19. ', '23')\n",
"('23', ' 20. ', '13')\n",
"('12', ' 21. ', '13')\n",
"('13', ' 22. ', '22')\n",
"('22', '23. ', '11')\n",
"(' 11', ' 24. ', '11')\n",
"('11', '25. ', '21')\n",
"('21', 'ж) утратил силу. - Правительства РФ от 16.08.2021 N 1337.26. ', '24')\n",
"('24', ' 28. ', '27')\n",
"('27', ' ', '22')\n",
"('22', '29. ', '24')\n",
"('24', ' 31. ', '37')\n",
"('37', ' (в ред. Правительства РФ от 16.08.2021 N 1337)32. ', '38')\n",
"('38', ' (в ред. Правительства РФ от 16.08.2021 N 1337)33. ', '35')\n",
"('2', ' сведения об организационной структуре реализации исследовательской программы, планы по изменению организационно-штатной структуры организации, на базе которой реализуется исследовательская программа, в целях обеспечения эффективной и независимой реализации исследовательской программы; ', '12')\n",
"('11', ' отказ от участия в конкурсе. ', '15')\n",
"('21', ' недостоверность информации, содержащейся в представленных организацией документах, указанных в настоящих Правил; ', '2')\n",
"('38', ' В случае установления в ходе проверок, проведенных Министерством науки и высшего образования Российской Федерации и (или) органом государственного финансового контроля, фактов нарушения целей, условий и порядка предоставления гранта средства гранта в размере, определенном на основании выявленных нарушений, подлежат возврату в доход федерального бюджета: ', '238')\n",
"('27', 'Результатом предоставления грантов является количество завершенных проектов открытых библиотек, размещенных в открытом доступе в информационно-телекоммуникационной сети \"Интернет\" и предоставляемых любым лицам на условиях безвозмездной бессрочной открытой лицензии, завершенных технологических проектов и проектов по акселерации, по которым завершена акселерационная программа. ', '22')\n",
"('36', ' при получении кредита по льготной процентной ставке направлять ежеквартально в Министерство строительства и жилищно-коммунального хозяйства Российской Федерации актуальную информацию об имеющихся депозитах и иных финансовых документах. ', '136')\n",
"('10', 'даты размещения результатов отбора на едином портале и на сайте http://favt.ru/ в сети \"Интернет\", которая не может быть позднее 14-го календарного дня, следующего за днем определения победителя отбора (принятия решения о заключении договора о предоставлении субсидии или об отказе в заключении договора). ', '7')\n",
"('10', ' наименование производителей, с которыми заключается соглашение, и размер предоставляемой субсидии. ', '11')\n",
"('37', ' Министерство промышленности и торговли Российской Федерации и органы государственного финансового контроля проводят проверки соблюдения производителем целей, условий и порядка предоставления субсидии, которые предусмотрены настоящими Правилами. ', '35')\n",
"('30', ' оплата услуг по переводам документов, аудиторских, бухгалтерских, юридических и консультационных услуг, а также патентных и нотариальных услуг, услуг по таможенному оформлению, по проведению экспертиз и получению заключений, связанных с производственной деятельностью и эксплуатацией технического оборудования; ', '33')\n",
"('11', 'соответствовать следующим требованиям:', '18')\n",
"('26', 'порядок согласования новых условий соглашения о предоставлении гранта или расторжения соглашения о предоставлении гранта при недостижении согласия по новым условиям в случае уменьшения ранее доведенных до Министерства промышленности и торговли Российской Федерации лимитов бюджетных обязательств, приводящих к невозможности предоставления гранта в размере, определенном в соглашении о предоставлении гранта.', '2')\n",
"('1', '3. ', '24')\n",
"('24', '4. ', '10')\n",
"('10', '5. ', '23')\n",
"('23', '6. ', '24')\n",
"('24', '7. ', '19')\n",
"('19', '8. ', '26')\n",
"('26', '9. ', '19')\n",
"('19', '10. ', '38')\n",
"('38', '11. ', '35')\n",
"('35', '(п. 11 в ред. Правительства РФ от 21.04.2022 N 723) 12.', '10')\n",
"('10', '13. ', '26')\n",
"('26', '14. ', '37')\n",
"('37', '15. ', '35')\n",
"('35', '16. ', '19')\n",
"('19', '17. ', '26')\n",
"('26', '18. ', '20')\n",
"('20', '19. ', '16')\n",
"('16', '20. ', '20')\n",
"('20', '21. ', '35')\n",
"('35', '23. ', '24')\n",
"('24', '24. ', '35')\n",
"('35', '26. ', '22')\n",
"('22', '27. ', '19')\n",
"('19', '28. ', '38')\n",
"('38', '29. ', '3')\n",
"('3', '30. ', '38')\n",
"('38', '31. ', '37')\n",
"('37', '', '27')\n",
"('27', '35. ', '37')\n",
"('37', '37. ', '38')\n",
"('3', ' формирование и ведение которого осуществляется Министерством финансов Российской Федерации в установленном им порядке при формировании проекта федерального закона о федеральном бюджете (проекта федерального закона о внесении изменений в федеральный закон о федеральном бюджете). ', ' 3')\n",
"('38', 'Возврат указанной суммы денежных средств осуществляется в порядке, предусмотренном бюджетным законодательством Российской Федерации. ', '35')\n",
"('24', 'Федеральное агентство по туризму не позднее 10-го рабочего дня со дня принятия решения о заключении соглашения о предоставлении субсидии заключает с организацией указанное соглашение по форме, установленной Министерством финансов Российской Федерации. ', '36')\n",
"('30', ' оплата услуг по переводам документов, аудиторских, бухгалтерских, юридических и консультационных услуг, а также патентных и нотариальных услуг, услуг по таможенному оформлению, по проведению экспертиз и получению заключений, связанных с производственной деятельностью и эксплуатацией технического оборудования; ', '33')\n",
"('38', 'на основании требования Федерального агентства по делам молодежи - не позднее 10-го рабочего дня со дня получения получателем гранта указанного требования;', '37')\n",
"('22', 'предельный размер гранта; ', '24')\n",
"('38', 'III. Особенности предоставления субсидии в части поддержкипроектов, предусматривающих разработку стандартных образцов(введен Правительства РФ от 14.04.2022 N 653)27. ', '33')\n",
"('33', '28. ', '5')\n",
"('5', ' ', '24')\n",
"('24', 'б) ', '36')\n",
"('36', 'в) ', '27')\n",
"('27', 'г) ', '32')\n",
"('32', 'д) ', '24')\n",
"('24', 'е) ', '37')\n",
"('37', ';ж) ', '38')\n",
"('38', 'з) ', '31')\n",
"('31', 'и) ', '38')\n",
"('38', 'к) ', '24')\n",
"('24', 'л) ', '25')\n",
"('25', 'м) ', '24')\n",
"('24', 'н) ', '26')\n",
"('26', 'о) ', '24')\n",
"('24', '29. ', '22')\n",
"('22', '30. ', '30')\n",
"('30', '31. ', '19')\n",
"('19', '32. ', '20')\n",
"('20', '', '21')\n",
"('21', '', '14')\n",
"('14', '', '24')\n",
"('24', '34. ', '27')\n",
"('27', '35. ', '36')\n",
"('36', '37. ', '35')\n",
"('35', 'ж) ', '7')\n",
"('7', 'з) ', '35')\n",
"('35', '38. ', '8')\n",
"('8', '', '10')\n",
"('10', 'р) ', '17')\n",
"('17', '39. ', '11')\n",
"('11', '', '12')\n",
"('12', '40. ', '19')\n",
"('19', '41. ', '24')\n",
"('24', 'б) ', '22')\n",
"('22', 'г) ', '30')\n",
"('30', 'д) ', '24')\n",
"('24', 'е) ', '36')\n",
"('36', 'з) ', '24')\n",
"('24', 'и) ', '38')\n",
"('38', 'к) ', '31')\n",
"('31', 'л) ', '24')\n",
"('24', 'о) ', '27')\n",
"('27', ' ', '38')\n",
"('38', 'п) ', '24')\n",
"('24', 'р) ', '26')\n",
"('26', 'с) ', '24')\n",
"('24', 'у) ', '38')\n",
"('38', '42. ', '35')\n",
"('35', '43. ', '27')\n",
"('27', '44. ', '29')\n",
"('29', '', '28')\n",
"('28', '45. ', '37')\n",
"('37', '46. ', '38')\n",
"('20', 'Министерство науки и высшего образования Российской Федерации рассматривает документы, указанные в настоящих Правил, и в 20-дневный срок со дня их поступления принимает решение о заключении соглашения или об отказе в заключении соглашения, о чем уведомляет оператора в течение 5 рабочих дней со дня принятия решения', '19')\n",
"('19', '(пп. \"ж\" введен Правительства РФ от 30.12.2020 N 2373)7. ', '20')\n",
"('20', '', '21')\n",
"('21', '(в ред. Правительства РФ от 30.12.2020 N 2373)8. ', '27')\n",
"('27', '9. ', '29')\n",
"('29', ' ', '28')\n",
"('28', '(п. 9 в ред. Правительства РФ от 30.12.2020 N 2373)10. Утратил силу. - Правительства РФ от 30.12.2020 N 2373.11. ', '36')\n",
"('36', '12. ', '37')\n",
"('37', '13. ', '38')\n",
"('11', ' организация не является иностранным юридическим лицом, а также российским юридическим лицом, в уставном (складочном) капитале которого доля участия иностранных юридических лиц, местом регистрации которых является государство или территория, ', '24')\n",
"('24', 'включенные в утвержденный Министерством финансов Российской Федерации государств и территорий, предоставляющих льготный налоговый режим налогообложения и (или) не предусматривающих раскрытия и предоставления информации при проведении финансовых операций (офшорные зоны), в совокупности превышает 50 процентов; ', '11')\n",
"('11) за исключением случаев, если указанные иностранные юридические лица находятся под контролем российских юридических лиц или физических лиц (конечными бенефициарами являются Российская Федерация, российские юридические лица или физические лица), в том числе в случае, если этот контроль осуществляется через иные иностранные юридические лица; {11', 'з) ', '11')\n",
"('11', '9. ', '35')\n",
"('35', '11. ', '15')\n",
"('15', '12. ', '35')\n",
"('35', '15. ', '19')\n",
"('19', '', '11')\n",
"('11', '16. ', '19')\n",
"('19', '17. ', '20')\n",
"('20', '', '21')\n",
"('21', '19. ', '35')\n",
"('35', '', '22')\n",
"('22', '20. ', '35')\n",
"('35', '21. ', '24')\n",
"('24', '22. ', '26')\n",
"('26', 'д) ', '25')\n",
"('25', 'е) ', '26')\n",
"('26', '23. ', '35')\n",
"('35', '24. ', '6')\n",
"('6', '25. ', '22')\n",
"('22', '26. ', '19')\n",
"('19', '', '20')\n",
"('20', '27. ', '35')\n",
"('35', '28. ', '3')\n",
"('3', 'а) ', '20')\n",
"('20', 'б) ', '29')\n",
"('29', ' ', '28')\n",
"('28', '29. ', '21')\n",
"('21', '30. ', '35')\n",
"('35', '31. ', '36')\n",
"('36', '34. ', '27')\n",
"('27', '35. ', '35')\n",
"('35', '36. ', '37')\n",
"('37', '37. ', '38')\n",
"('25', ' Министерство экономического развития Российской Федерации:', '35')\n",
"('10', 'доменное имя, и (или) сетевой адрес, и (или) указатели страниц сайта в информационно-телекоммуникационной сети \"Интернет\", на котором обеспечивается проведение отбора; ', '24')\n",
"('15', ' обязательство Фонда о проведении отбора в соответствии с порядком, установленным настоящих Правил; ', '24')\n",
"('27', 'значения показателей, необходимых для достижения результата предоставления субсидии, указанные в настоящих Правил; ', '24')\n",
"('10', ' кредитная организация по состоянию на дату не ранее чем за 30 календарных дней до даты подачи заявки на получение субсидии не имеет просроченной задолженности по возврату в федеральный бюджет субсидий, бюджетных инвестиций, предоставленных из федерального бюджета в том числе в соответствии с иными правовыми актами, и иной просроченной (неурегулированной) задолженности по денежным обязательствам перед Российской Федерацией; ', '12')\n",
"('35', ' включения заемщика, содержащегося в реестре потенциальных заемщиков, в реестр заемщиков устанавливается ', '3')\n",
"('3', '', '35')\n",
"('22', ' Размер субсидии (S) по направлениям ее использования рассчитывается по формуле: ', '21')\n",
"('30', 'Расходы на оплату труда работников, на начисления на выплаты по оплате труда работников в соответствии с законодательством Российской Федерации, а также на иные указанные в настоящих Правил направления расходов не могут превышать 15 процентов размера субсидии.', '3')\n",
"('22', ' Si_март - размер субсидии i-му российскому аэропорту за март, рублей; ', '221')\n",
"('где:{22', ' Рмарт - размер расходной ставки аэропорта за март, равный 772 рублям на 1 \"потерянного\" пассажира, руб./пасс.; ', '22')\n",
"('22', ' Si_март - размер субсидии i-му российскому аэропорту за март, рублей; ', '221')\n",
"('где:{22', ' Рмарт - размер расходной ставки аэропорта за март, равный 772 рублям на 1 \"потерянного\" пассажира, руб./пасс.; ', '22')\n",
"('38', 'где: ', '22')\n",
"('22', '22. ', '38')\n",
"('36', ' сроки и формы представления отчета оператором о ходе реализации программ по развитию отдельных направлений Национальной технологической инициативы и отчета о расходах, источником финансового обеспечения которых является субсидия, а также отчета о достижении значения результата предоставления субсидии в соответствии с настоящих Правил;', '46')\n",
"('4', ' цели, условия и порядок предоставления и использования гранта;', '2')\n",
"('16', ' Отбор проводится образуемой Министерством промышленности и торговли Российской Федерации комиссией по проведению отбора (далее - комиссия). ', '316')\n",
"('12', ' выписка из Единого государственного реестра юридических лиц, заверенная в установленном порядке (в случае непредставления российской компанией такого документа Министерство промышленности и торговли Российской Федерации запрашивает его самостоятельно); ', '13')\n",
"('24', ' Основаниями для расторжения соглашения, в том числе расторжения соглашения Министерством промышленности и торговли Российской Федерации в одностороннем порядке, являются: ', '21')\n",
"('', '15указанных в настоящих Правил, полноту содержащихся в них сведений и направляет их на рассмотрение Комиссии. ', '15')\n",
"('15', ' заключает с производителями соглашения о предоставлении субсидии в течение 15 рабочих дней со дня окончания проверки, предусмотренной настоящего пункта. ', '35')\n",
"('35', 'уведомляет об этом производителя и возвращает заявление о включении в реестр получателей субсидии по договорам о реализации, заключенным в 2018 - 2019 годах, и документы, представленные производителем в соответствии с настоящих Правил; ', '15')\n",
"('7', 'Субсидии в целях осуществления мероприятий по приобретению объектов особо ценного движимого имущества в части транспортных средств. ', '2')\n",
"('35', 'отсутствие бюджетных ассигнований федерального бюджета, предусмотренных в целях предоставления субсидии.', '38')\n",
"('28', 'В случае если совокупный размер выплаты за период оплаты не превышает объем лимитов бюджетных обязательств, доведенных до ', '3')\n",
"('3', ' в соответствии с настоящих Правил, Федеральное агентство по туризму вправе установить очередной период оплаты.', '28')\n",
"('11', ' основные направления деятельности некоммерческой организации в соответствии с учредительными документами должны соответствовать тематике конкурса, в котором участвует некоммерческая организация; ', '25')\n",
"('26', ' Соглашение о предоставлении субсидии (дополнительное соглашение к соглашению о предоставлении субсидии, в том числе дополнительное соглашение о расторжении соглашения о предоставлении субсидии) с соблюдением требований о защите государственной тайны заключается', '24')\n",
"('38', 'В случае если требование, указанное в настоящих Правил, не выполнено в установленный срок, организация возвращает в федеральный бюджет полученные средства на основании: ', '36')\n",
"('21', 'Основаниями для отказа в предоставлении обществу субсидии являются: ', '23')\n",
"('27', 'Результатом предоставления субсидии является обеспечение страховой и гарантийной поддержки в отношении проектов, включенных в перечень. ', '28')\n",
"('11', 'соответствовать следующим требованиям:', '18')\n",
"('20', 'Перечисление субсидии получателю субсидии осуществляется на казначейский счет для осуществления и отражения операций с денежными средствами юридических лиц, не являющихся участниками бюджетного процесса, бюджетными и автономными учреждениями, открытый в территориальном органе Федерального казначейства, ', '29')\n",
"('37', 'Федеральное агентство воздушного транспорта осуществляет проверку соблюдения авиакомпанией условий и порядка предоставления субсидий, в том числе в части достижения результата предоставления субсидии, а органы государственного финансового контроля осуществляют проверки в соответствии со и Бюджетного кодекса Российской Федерации.', '7')\n"
]
}
],
"source": [
"#load data\n",
"\n",
"all_text, all_groups, doc_paths, doc_names = [],[],[],[]\n",
"for d in documents:\n",
" if 'ipynb' not in d:\n",
" text = get_text(d)\n",
" texts,groups = split_text(text)\n",
" all_text.extend(texts)\n",
" all_groups.extend(groups)\n",
" doc_paths.extend([d for a in range(len(texts))])\n",
" doc_names.extend([d.split('/')[-1] for a in range(len(texts))])"
]
},
{
"cell_type": "code",
"execution_count": 6,
"id": "1413bdb0-ed8d-453d-9b67-fde0cfacd4e5",
"metadata": {},
"outputs": [],
"source": [
"#load documents\n",
"#apply preprocessing to documents\n",
"\n",
"df = pd.DataFrame([doc_paths, doc_names,all_text, all_groups]).T\n",
"df.columns = ['path','doc','text','type']\n",
"df['r_text']='r'\n",
"df['r_text'] = df.text.apply(lowercase)\n",
"df['r_text'] = df.r_text.apply(clean_symb)\n",
"df['r_text'] = df.r_text.apply(lambda x:''.join([a for a in x if not a.isdigit()]))\n",
"df['r_text'] = df.r_text.apply(lambda x:' '.join([a for a in x.split(' ') if len(a)>1]))\n",
"df['r_text'] = df.r_text.apply(clean_stopwords)\n",
"df['text_size'] = df['text'].apply(lambda x: len(x.strip()))\n",
"df['is_text'] = df.r_text.apply(lambda x:x.strip().isdigit())\n",
"df = df[~df.is_text]\n",
"df = df[df['text_size']>5]\n",
"df = df.reset_index(drop=True)\n",
"df.shape\n",
"df.type = df.type.astype(int)-1"
]
},
{
"cell_type": "code",
"execution_count": 7,
"id": "1f4d8205-7f3f-430b-ac84-9e19ee913f81",
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"правил 3588\n",
"организации 2263\n",
"отбора 2042\n",
"соглашения 1940\n",
"предоставлении 1747\n",
"результата 1578\n",
"гранта 1556\n",
"министерством 1544\n",
"дня 1360\n",
"заявок 1344\n",
"dtype: int64"
]
},
"execution_count": 7,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"#show most popular words in datset\n",
"\n",
"all_words = np.hstack([np.array(a) for a in df.r_text.apply(lambda x:[a for a in x.split(' ') if len(a)>0]).values])\n",
"pd.Series(all_words).value_counts()[:10]"
]
},
{
"cell_type": "code",
"execution_count": 8,
"id": "4c22b4c2-9155-4655-bc95-6e3387b28ac4",
"metadata": {},
"outputs": [],
"source": [
"#split data to train/test\n",
"\n",
"from sklearn.utils import resample\n",
"from sklearn.model_selection import train_test_split\n",
"\n",
"X_data, X_val, y_data, y_val = train_test_split(list(df['r_text']), list(df['type']), test_size=0.1, random_state=42)"
]
},
{
"cell_type": "code",
"execution_count": 9,
"id": "eaac3775-7552-49c7-a891-c8ef5cccf6d9",
"metadata": {},
"outputs": [],
"source": [
"import numpy as np\n",
"import torch\n",
"from transformers import BertTokenizer, BertForSequenceClassification\n",
"from torch.utils.data import Dataset, DataLoader\n",
"from transformers import AdamW, get_linear_schedule_with_warmup\n",
"\n",
"from bert_dataset import CustomDataset"
]
},
{
"cell_type": "code",
"execution_count": 11,
"id": "c75236ca-e832-4748-a312-9cc7f7935f51",
"metadata": {},
"outputs": [],
"source": [
"#Bert Classifier class\n",
"\n",
"class BertClassifier:\n",
"\n",
" def __init__(self, model_path, tokenizer_path, n_classes=2, epochs=1, model_save_path='/content/bert.pt'):\n",
" self.model = BertForSequenceClassification.from_pretrained(model_path)\n",
" self.tokenizer = BertTokenizer.from_pretrained(tokenizer_path)\n",
" self.device = torch.device(\"cuda:0\" if torch.cuda.is_available() else \"cpu\")\n",
" self.model_save_path=model_save_path\n",
" self.max_len = 512\n",
" self.epochs = epochs\n",
" self.out_features = self.model.bert.encoder.layer[1].output.dense.out_features\n",
" self.model.classifier = torch.nn.Linear(self.out_features, n_classes)\n",
" self.model.to(self.device)\n",
" \n",
" def preparation(self, X_train, y_train, X_valid, y_valid):\n",
" # create datasets\n",
" self.train_set = CustomDataset(X_train, y_train, self.tokenizer)\n",
" self.valid_set = CustomDataset(X_valid, y_valid, self.tokenizer)\n",
"\n",
" # create data loaders\n",
" self.train_loader = DataLoader(self.train_set, batch_size=8, shuffle=True)\n",
" self.valid_loader = DataLoader(self.valid_set, batch_size=8, shuffle=True)\n",
"\n",
" # helpers initialization\n",
" self.optimizer = AdamW(self.model.parameters(), lr=2e-5, correct_bias=False)\n",
" self.scheduler = get_linear_schedule_with_warmup(\n",
" self.optimizer,\n",
" num_warmup_steps=0,\n",
" num_training_steps=len(self.train_loader) * self.epochs\n",
" )\n",
" self.loss_fn = torch.nn.CrossEntropyLoss().to(self.device)\n",
" \n",
" def fit(self):\n",
" self.model = self.model.train()\n",
" losses = []\n",
" correct_predictions = 0\n",
"\n",
" for data in tqdm(self.train_loader):\n",
" input_ids = data[\"input_ids\"].to(self.device)\n",
" attention_mask = data[\"attention_mask\"].to(self.device)\n",
" targets = data[\"targets\"].to(self.device)\n",
"\n",
" outputs = self.model(\n",
" input_ids=input_ids,\n",
" attention_mask=attention_mask\n",
" )\n",
"\n",
" preds = torch.argmax(outputs.logits, dim=1)\n",
" loss = self.loss_fn(outputs.logits, targets)\n",
"\n",
" correct_predictions += torch.sum(preds == targets)\n",
"\n",
" losses.append(loss.item())\n",
" \n",
" loss.backward()\n",
" torch.nn.utils.clip_grad_norm_(self.model.parameters(), max_norm=1.0)\n",
" self.optimizer.step()\n",
" self.scheduler.step()\n",
" self.optimizer.zero_grad()\n",
"\n",
" train_acc = correct_predictions.double() / len(self.train_set)\n",
" train_loss = np.mean(losses)\n",
" return train_acc, train_loss\n",
" \n",
" def eval(self):\n",
" self.model = self.model.eval()\n",
" losses = []\n",
" correct_predictions = 0\n",
"\n",
" with torch.no_grad():\n",
" for data in self.valid_loader:\n",
" input_ids = data[\"input_ids\"].to(self.device)\n",
" attention_mask = data[\"attention_mask\"].to(self.device)\n",
" targets = data[\"targets\"].to(self.device)\n",
"\n",
" outputs = self.model(\n",
" input_ids=input_ids,\n",
" attention_mask=attention_mask\n",
" )\n",
"\n",
" preds = torch.argmax(outputs.logits, dim=1)\n",
" loss = self.loss_fn(outputs.logits, targets)\n",
" correct_predictions += torch.sum(preds == targets)\n",
" losses.append(loss.item())\n",
" \n",
" val_acc = correct_predictions.double() / len(self.valid_set)\n",
" val_loss = np.mean(losses)\n",
" return val_acc, val_loss\n",
" \n",
" def train(self):\n",
" best_accuracy = 0\n",
" for epoch in range(self.epochs):\n",
" print(f'Epoch {epoch + 1}/{self.epochs}')\n",
" train_acc, train_loss = self.fit()\n",
" print(f'Train loss {train_loss} accuracy {train_acc}')\n",
"\n",
" val_acc, val_loss = self.eval()\n",
" print(f'Val loss {val_loss} accuracy {val_acc}')\n",
" print('-' * 10)\n",
"\n",
" if val_acc > best_accuracy:\n",
" torch.save(self.model, self.model_save_path)\n",
" best_accuracy = val_acc\n",
"\n",
" self.model = torch.load(self.model_save_path)\n",
" \n",
" def predict(self, text):\n",
" encoding = self.tokenizer.encode_plus(\n",
" text,\n",
" add_special_tokens=True,\n",
" max_length=self.max_len,\n",
" return_token_type_ids=False,\n",
" truncation=True,\n",
" padding='max_length',\n",
" return_attention_mask=True,\n",
" return_tensors='pt',\n",
" )\n",
" \n",
" out = {\n",
" 'text': text,\n",
" 'input_ids': encoding['input_ids'].flatten(),\n",
" 'attention_mask': encoding['attention_mask'].flatten()\n",
" }\n",
" \n",
" input_ids = out[\"input_ids\"].to(self.device)\n",
" attention_mask = out[\"attention_mask\"].to(self.device)\n",
" \n",
" outputs = self.model(\n",
" input_ids=input_ids.unsqueeze(0),\n",
" attention_mask=attention_mask.unsqueeze(0)\n",
" )\n",
" \n",
" prediction = torch.argmax(outputs.logits, dim=1).cpu().numpy()[0]\n",
"\n",
" return prediction"
]
},
{
"cell_type": "code",
"execution_count": 12,
"id": "38cf183b-a3ee-4ef2-94b9-051bcb8918c7",
"metadata": {},
"outputs": [
{
"name": "stderr",
"output_type": "stream",
"text": [
"Some weights of the model checkpoint at sberbank-ai/ruBert-base were not used when initializing BertForSequenceClassification: ['cls.predictions.bias', 'cls.predictions.transform.dense.weight', 'cls.predictions.transform.dense.bias', 'cls.predictions.transform.LayerNorm.weight', 'cls.predictions.transform.LayerNorm.bias', 'cls.predictions.decoder.weight', 'cls.predictions.decoder.bias', 'cls.seq_relationship.weight', 'cls.seq_relationship.bias']\n",
"- This IS expected if you are initializing BertForSequenceClassification from the checkpoint of a model trained on another task or with another architecture (e.g. initializing a BertForSequenceClassification model from a BertForPreTraining model).\n",
"- This IS NOT expected if you are initializing BertForSequenceClassification from the checkpoint of a model that you expect to be exactly identical (initializing a BertForSequenceClassification model from a BertForSequenceClassification model).\n",
"Some weights of BertForSequenceClassification were not initialized from the model checkpoint at sberbank-ai/ruBert-base and are newly initialized: ['classifier.weight', 'classifier.bias']\n",
"You should probably TRAIN this model on a down-stream task to be able to use it for predictions and inference.\n"
]
}
],
"source": [
"#make bert\n",
"\n",
"classifier = BertClassifier(\n",
" model_path='sberbank-ai/ruBert-base',\n",
" tokenizer_path='sberbank-ai/ruBert-base',\n",
" n_classes=39,\n",
" epochs=10,\n",
" model_save_path='bert_fit_models/bert.pt'\n",
")"
]
},
{
"cell_type": "code",
"execution_count": 13,
"id": "2b3a3cb5-1dd5-42aa-9df7-903604ba28c4",
"metadata": {},
"outputs": [],
"source": [
"#prepare data to classification\n",
"classifier.preparation(\n",
" X_train=list(X_data),\n",
" y_train=list(y_data),\n",
" X_valid=list(X_val),\n",
" y_valid=list(y_val),\n",
" )"
]
},
{
"cell_type": "code",
"execution_count": 13,
"id": "54dacb80-c43f-47b1-83f9-490ad0d6d176",
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"Epoch 1/10\n"
]
},
{
"name": "stderr",
"output_type": "stream",
"text": [
"100%|███████████████████████████████████████| 1960/1960 [24:31<00:00, 1.33it/s]\n"
]
},
{
"name": "stdout",
"output_type": "stream",
"text": [
"Train loss 1.6872646148563648 accuracy 0.5666815485681486\n",
"Val loss 1.412977649804649 accuracy 0.6115892139988525\n",
"----------\n",
"Epoch 2/10\n"
]
},
{
"name": "stderr",
"output_type": "stream",
"text": [
"100%|███████████████████████████████████████| 1960/1960 [24:32<00:00, 1.33it/s]\n"
]
},
{
"name": "stdout",
"output_type": "stream",
"text": [
"Train loss 1.1436501777863928 accuracy 0.6886918808597488\n",
"Val loss 1.2984553687616225 accuracy 0.6374067699368904\n",
"----------\n",
"Epoch 3/10\n"
]
},
{
"name": "stderr",
"output_type": "stream",
"text": [
"100%|███████████████████████████████████████| 1960/1960 [24:32<00:00, 1.33it/s]\n"
]
},
{
"name": "stdout",
"output_type": "stream",
"text": [
"Train loss 0.9005808831667718 accuracy 0.7508131896166848\n",
"Val loss 1.2479785930946332 accuracy 0.6666666666666666\n",
"----------\n",
"Epoch 4/10\n"
]
},
{
"name": "stderr",
"output_type": "stream",
"text": [
"100%|███████████████████████████████████████| 1960/1960 [24:32<00:00, 1.33it/s]\n"
]
},
{
"name": "stdout",
"output_type": "stream",
"text": [
"Train loss 0.7234191348244037 accuracy 0.7962242489954717\n",
"Val loss 1.2792062138062004 accuracy 0.6580608146873207\n",
"----------\n",
"Epoch 5/10\n"
]
},
{
"name": "stderr",
"output_type": "stream",
"text": [
"100%|███████████████████████████████████████| 1960/1960 [24:30<00:00, 1.33it/s]\n"
]
},
{
"name": "stdout",
"output_type": "stream",
"text": [
"Train loss 0.5877058356572703 accuracy 0.8332164041074048\n",
"Val loss 1.3536883816464778 accuracy 0.6678141135972461\n",
"----------\n",
"Epoch 6/10\n"
]
},
{
"name": "stderr",
"output_type": "stream",
"text": [
"100%|███████████████████████████████████████| 1960/1960 [24:30<00:00, 1.33it/s]\n"
]
},
{
"name": "stdout",
"output_type": "stream",
"text": [
"Train loss 0.49206937486923547 accuracy 0.8616620957969259\n",
"Val loss 1.4424607625248236 accuracy 0.6752725186460126\n",
"----------\n",
"Epoch 7/10\n"
]
},
{
"name": "stderr",
"output_type": "stream",
"text": [
"100%|███████████████████████████████████████| 1960/1960 [24:25<00:00, 1.34it/s]\n"
]
},
{
"name": "stdout",
"output_type": "stream",
"text": [
"Train loss 0.40955075885392533 accuracy 0.8821353402640475\n",
"Val loss 1.5361568299250319 accuracy 0.6620768789443487\n",
"----------\n",
"Epoch 8/10\n"
]
},
{
"name": "stderr",
"output_type": "stream",
"text": [
"100%|███████████████████████████████████████| 1960/1960 [24:25<00:00, 1.34it/s]\n"
]
},
{
"name": "stdout",
"output_type": "stream",
"text": [
"Train loss 0.3543910782568024 accuracy 0.899292046686651\n",
"Val loss 1.6124461362428895 accuracy 0.6712564543889844\n",
"----------\n",
"Epoch 9/10\n"
]
},
{
"name": "stderr",
"output_type": "stream",
"text": [
" 58%|██████████████████████▌ | 1132/1960 [14:04<10:16, 1.34it/s]IOPub message rate exceeded.\n",
"The Jupyter server will temporarily stop sending output\n",
"to the client in order to avoid crashing it.\n",
"To change this limit, set the config variable\n",
"`--ServerApp.iopub_msg_rate_limit`.\n",
"\n",
"Current values:\n",
"ServerApp.iopub_msg_rate_limit=1000.0 (msgs/sec)\n",
"ServerApp.rate_limit_window=3.0 (secs)\n",
"\n"
]
}
],
"source": [
"#train\n",
"classifier.train()"
]
},
{
"cell_type": "code",
"execution_count": 20,
"id": "8dece2c7-b3be-4e69-b51b-a5a1b70bfaaf",
"metadata": {},
"outputs": [],
"source": [
"#save best model again\n",
"\n",
"torch.save(classifier.model,'bert_magnus_opum.pt')"
]
},
{
"cell_type": "code",
"execution_count": 10,
"id": "0e3977a9-ddeb-46e1-9b2a-46fc7b31ea1a",
"metadata": {
"tags": []
},
"outputs": [],
"source": [
"#load bert and truncate last layer\n",
"#get the embeddings layer\n",
"\n",
"model = torch.load('bert_opossum_best_0.6753.pt')\n",
"model = model.bert\n",
"model.to(device)\n",
"pass\n",
"\n",
"#load tokenizer\n",
"tokenizer = BertTokenizer.from_pretrained('sberbank-ai/ruBert-base')"
]
},
{
"cell_type": "code",
"execution_count": 11,
"id": "defe53ec-baa1-45f8-8d52-74ef2b425828",
"metadata": {},
"outputs": [],
"source": [
"#get token and embedding functions\n",
"\n",
"def get_token(text):\n",
" return tokenizer.encode_plus(\n",
" text,\n",
" add_special_tokens=True,\n",
" max_length=512,\n",
" return_token_type_ids=False,\n",
" truncation=True,\n",
" padding='max_length',\n",
" return_attention_mask=True,\n",
" return_tensors='pt')\n",
"\n",
"def get_embeddings(text):\n",
" encoding = get_token(text)\n",
" out = {\n",
" 'text': text,\n",
" 'input_ids': encoding['input_ids'].flatten(),\n",
" 'attention_mask': encoding['attention_mask'].flatten()\n",
" }\n",
"\n",
" input_ids = out[\"input_ids\"].to(device)\n",
" attention_mask = out[\"attention_mask\"].to(device)\n",
"\n",
" outputs = model(\n",
" input_ids=input_ids.unsqueeze(0),\n",
" attention_mask=attention_mask.unsqueeze(0)\n",
" )\n",
" return outputs[1].cpu().detach().numpy()[0]"
]
},
{
"cell_type": "code",
"execution_count": 12,
"id": "14627fdd-fa38-4cb8-b4c0-70a83f22c00e",
"metadata": {},
"outputs": [
{
"name": "stderr",
"output_type": "stream",
"text": [
"100%|█████████████████████████████████████| 17422/17422 [10:11<00:00, 28.48it/s]\n"
]
}
],
"source": [
"#get embeddings from text\n",
"\n",
"df['emb'] = df.r_text.progress_apply(get_embeddings)"
]
},
{
"cell_type": "code",
"execution_count": 45,
"id": "b23c2f54-9533-4fac-a28f-db02f97d4ce6",
"metadata": {},
"outputs": [],
"source": [
"#split data again\n",
"\n",
"X_full = np.asarray([a for a in df['emb'].values])\n",
"y_full = df['type'].values.astype(int)\n",
"\n",
"X_data, X_val, y_data, y_val = train_test_split(X_full, y_full, test_size=0.1, random_state=42)"
]
},
{
"cell_type": "code",
"execution_count": 46,
"id": "142b7f1a-4701-48a0-a801-f275efe683a4",
"metadata": {},
"outputs": [],
"source": [
"## check upsampling data\n",
"## permutation data\n",
"\n",
"\n",
"np.random.seed(77112)\n",
"\n",
"class_size=833\n",
"X_data_r, y_data_r = [],[]\n",
"\n",
"\n",
"for d in np.unique(y_data):\n",
" X_data_r.append(resample(X_data[y_data==d],\n",
" replace=True,\n",
" n_samples=833,\n",
" random_state=42))\n",
" y_data_r.append(np.full([class_size],d))\n",
"\n",
"X_data, y_data = np.vstack(X_data_r), np.hstack(y_data_r)\n",
"\n",
"permutations = np.random.permutation(len(X_data))\n",
"\n",
"X_data, y_data = X_data[permutations], y_data[permutations]"
]
},
{
"cell_type": "code",
"execution_count": 47,
"id": "dc89ab58-527d-4691-8ae0-37281426f3e9",
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"(32487, 768)"
]
},
"execution_count": 47,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"X_data.shape"
]
},
{
"cell_type": "code",
"execution_count": 48,
"id": "565440c4-0f36-4b20-804b-74ea26e03fdc",
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"0.03843947217441193\n"
]
},
{
"data": {
"text/plain": [
"<AxesSubplot:xlabel='real'>"
]
},
"execution_count": 48,
"metadata": {},
"output_type": "execute_result"
},
{
"data": {
"image/png": "iVBORw0KGgoAAAANSUhEUgAAAjIAAAHBCAYAAABzIlFzAAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjUuMywgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy/NK7nSAAAACXBIWXMAAA9hAAAPYQGoP6dpAABhEUlEQVR4nO3deXhMZ/sH8O9MIsSSxL4k9lYskUUlaGILYhdaeXWhaGhaaq23dKG0iqpSpQhSrdIFbb2tfadUayliF7WlhGyyNYkkM/fvD785NbLNDJPMSb6f6+pVOfPc89zPec5M7pw55xmNiAiIiIiIVEhb3AkQERERWYqFDBEREakWCxkiIiJSLRYyREREpFosZIiIiEi1WMgQERGRarGQISIiItViIUNERESqZV/cCTxuIgK9Pvcaf1qtJs/tBbHVGOZVesdiq3lZEmOreVkSw7xK71hsNS9LYoozL61WA41GY9bzGJS4QkavFyQm/mO0zd5ei8qVKyAlJR05OXqTnsdWY5hX6R2LreZlSYyt5mVJDPMqvWOx1bwsiSnuvKpUqQA7O8sKGX60RERERKrFQoaIiIhUi4UMERERqRYLGSIiIlItFjJERESkWiXuriUiIiJz6fV6ZGXlIDPTDllZ96DTFX5LsV6vMau9LcdYsw87O3totdY7b8JChoiISi0RQUpKIjIy0gAA8fFa6PWm3UpsSXtbjrFmH46OFeHkVMWs5zaV2YXM9evXERERgVOnTiEqKgqNGjXCpk2blMf//vtvdOnSJc9YBwcHnD59usB2Xl5eWLdunblpERERmc1QxFSsWBkODmVhb681+YwEANjZacxqb8sx1uhDRJCVdQ9paXcBAFWrVjfr+U1hdiETFRWF/fv3w8vLC3q9HiLGA6hRowa+//57o20ighEjRqBt27a5nm/ixIlo06aN8nOFChXMTYmIiMhser1OKWIqVnQCcH/BNlMXd7OkvS3HWKsPB4eyAIC0tLvQ6x//WRmzC5nAwEB07doVADBlyhScOXPG6HEHBwd4e3sbbfvjjz+QlpaGPn365Hq++vXr52pPRERkbTqdDsC/v2jJegz7OCdH99if2+yrbyy5YGfTpk2oWLEiAgMDzY4lIiKyJku/44dM9+8+Nu+jK1NY/WLf7Oxs7NixA926dUPZsrmr3unTp2PChAlwcXFBly5dMGnSJLi4uDxSn/b2xsWWnZ3W6P+msNUY5lV6x2KreVkSY6t5WRLDvNQ7Fr3euIAx/K7VaAAx4fetue1tOaao8rJkLgtj9ULmwIEDSEpKyvWxkoODA55//nkEBATAyckJp06dwrJly3DmzBmsX78eZcqUsag/rVaDypXzvs7GycnR7Oez1RjmVXrHYqt5WRJjq3lZEsO81DeWzEw7xMdrYWenMfoD2M5OC41GA63WtDM1lvxSLrjAklzXn1qjn8fR3tQYvV4DrVaLihXLAbBsLvNj9ULml19+QbVq1dCuXTuj7TVq1MD06dOVn/38/PDkk08iLCwMO3fuRK9evSzqT68XpKSkG22zs9PCyckRKSkZ0OlMu5DJVmOYV+kdi63mZUmMreZlSQzzUu9YsrLuQa/XQ6cT5OToodHcjxMROLk4wk5TPGvG6kSPpMR06PX3ixlDXjqdPt8zHwcO7EN8fByeeSbE5JgHmdve3BidTqDX65GWloly5crlmhcnJ0eLz9JYtZD5559/sHfvXoSEhMDOzq7Q9h07dkT58uVx9uxZiwsZAPleQa3T6c2+IttWY5hX6R2LreZlSYyt5mVJDPNS31gevm3Y8MtYo9HATqNFBPYgBnfN6u9R1UZlhGoCodVqlELGkFdBxcKvv+7DhQvnlELGlJgHmdve0hhD8WLJXObHqoXMzp07kZmZib59+1qzGyIiVdBq739c8fB1Anq9KL+0yHbE4C6ikVDcaTw2IoLs7Gw4ODgUdyqPlVULmU2bNqFevXrw8vIyqf3evXuRnp6Oli1bWjMtIqIip9VqUMXFEZoHzk4brhMQnQ6JSRksZsgiH344HVu33l+YNiCgNQCgZ88+0Gg0OH/+LEaNGotlyz7H9etX8d57M5GRkYFZs2Zg06ZdRjfXDBnyHJ54ogneeWe6su3MmUgsX74E586dgZ2dHdq1C8C4cW+gcmXrrNJrCbMLmYyMDOzfvx8AcPPmTaSlpWHbtm0A7l/nUqXK/cElJibi8OHDGDlyZJ7PM2fOHGg0Gnh7e8PJyQmRkZEIDw+Hh4eHsk4NEVFJodVq7hcxERFATMy/D9SuDU1oqNFHCUTmGDZsBJKS7uL69WuYNm0mAKBy5cr46qsIxMfH49NP52Ho0FDUrFkLNWvWQmTkSZOe98yZSIwZE4a2bf0xY8ZsZGZmYMWKpZgy5Q2Eh6+y4ojMY3Yhk5CQgHHjxhltM/y8evVqZZXerVu3IicnJ9+PlRo3boxvv/0W69atQ2ZmJmrWrImBAwdi7NixsLfnV0ARUQkVEwNERxd3FlSCuLq6wcWlMm7fjoGHh/EnGqmpKZg37zO0aOGhbDO1kFm2bDGaNm2GWbM+VtaBadToCbz00iAcPnwQ7doFPLYxPAqzKwY3NzdcvHix0HYvvvgiXnzxxXwfDwkJQUhIiLndExERkYmcnZ2NihhTZWZm4vTpUxg9epyyAjIA1K1bDzVq1MT58+fUW8gQERGROlSuXNWiuNTUFOh0Onz22Xx89tn8XI/Hxt551NQeGxYyREREJVRe375guGspJyfbaHtqaory74oVK0Gj0WDIkOHo0KFTrudwdnZ5nGk+EhYyREREKmdvXwZZWVkmta1evSYA4Nq1q6hWrbry7zt3/j3L4ujoCA+Plrh+/SqaNh31+BN+jFjIEBER5aE2KqumzwYNGmDLlp+xc+c21K1br8AzJi1aeKBGjZpYtGg+wsJexz//pGHNmq/g7Oxs1G7UqHEYN+41TJv2Frp0CUKlSpUQFxeLo0f/QK9efdGqVWuLcn3cWMgQERE9QK8X6ESPUE1gsfSvE73Zt+L36ROMc+fO4tNPP0ZycrKyjkxe7O3tMWvWPHzyyWxMnToZbm51MWbMRHz++adG7Vq29MKSJSsRERGO2bNnIDs7G9Wr10Tr1r5wc6tr6fAeOxYyRERED9DrBUmJ6SZ9aaThu4bMUViMJSs9V6hQETNmzDLaZm+vzfdrAJo2bYYVK1Ybbfv66+9ytW/atDk+/nihWbkUNRYyREREDzGnmLDkO4Me1/cMEVA8X+1JRERE9BiwkCEiIiLVYiFDREREqsVChoiIiFSLhQwRERGpFgsZIiIiUi0WMkRERKRaLGSIiIhItbggHhER0UO0Wo3JK/uaq7AYS1b2BYDvv1+L77//BvHxcfD3b4+PP15QaMzAgX3x9NMBmDhxstn92QoWMkRERA/QajWo4uIIjZ1dsfQvOh0SkzLMKmaio29g8eJP8eKLQ+Hv377AL40saVjIEBERPUCr1dwvYiIigJiYou28dm1oQkOh1WrMKmRu3LgOEUHfvv3h6upmxQRtDwsZIiKivMTEANHRxZ1FoT78cDq2bt0EABg0qD8AYMKENxEdfQ1//PE7YmPvoHLlKmjTph1ee20sKlasmO9zXbnyF5YsWYhz587i3r1M1KhRE336BOPFF4cqbc6cicTy5Utw7twZ2NnZo107f4wb9wYqV65i1XHmh4UMERGRig0bNgINGjTE0qWL8OGHH6Nq1WpwdXXDF1+E45VXRsHFpTJiY+9g9eov8NZbb2DRovB8n2vy5ImoUqUKpkyZiooVK+Lvv6MRFxerPH7mTCTGjAlD27b+mDFjNrKyMhEevgRTpryB8PBVRTHcXFjIEBERqZirqxvq1q0PAGjSxB21a9cBAEye/LbyLds5OTmoXbsORo0agRs3rqNevfq5nicp6S5iYm5i3Lg3EBDQAQDQqlVrozbLli1G06bNMGvWx9BoNLC316JBg8Z46aVBOHz4INq1C7DmUPPEQoaIiKgE2rp1E775Zg3+/jsaGRkZyvbo6Bt5FjLOzi6oVas2wsMXIzU1BU895YsaNWoqj2dmZuL06VMYPXocdDrd/2/Vom7deqhRoybOnz/HQoaIiIge3f79ezFjxjT06zcAr7wyCk5OLkhIiMfbb09CVta9PGM0Gg3mz1+M5cuXYP78j5CRkQF392YYM2YCvL1bITU1BTqdDp99Nh+ffTY/V3xs7B1rDytPLGSIiIhKmL17d6FJE3e8+eY7yrYTJ44XGlevXn3MnPkRcnJycPr0KSxf/jkmT56An37aiooVK0Gj0WDIkOHo0KETgPtr4uh09z++Kq5bvlnIEBERlTD37t2DvX0Zo207dmwzOd7e3h4+Pk/hxReHYcqUiYiPj0O9evXh4dES169fRdOmo/6/nVa5Dqe4sJAhIiIqYXx922D+/I/w5Zcr0aJFS/z++yEcP36kwJioqEtYuHA+unQJgqurG9LS0vD116tQu3YdZW2aUaPGYdy41zBt2lvo0iUILi7OuH37No4e/QO9evXNdXFwUWAhQ0RElJfatVXbZ3DwM7h9+xY2bPge33zzNfz82uK99z5EWNiwfGOqVq2GqlWr4uuvVyE+Pg4VKlSEl5c3pk37AHb/v8pxy5ZeWLJkJSIiwjF79gxkZ+egevUaaN3aF25udR9L7uZiIUNERPQAvV4gOh00oaHF0r/odGZ/11KHDp1w8OAx5Wc7OzuMHTsBo0aNM2r3YBsA2LDhF+XfVapUwdSpHxTaV9OmzfHxxwsB8KMlIiIim6PXCxKTMkz+0kjDxa6mKizG0i+NLK1YyBARET3EnGLCkjMSxX0WoyQx//vHiYiIiGwECxkiIiJSLRYyREREpFosZIiIqFQT4YW11vbvPi78AmpzsZAhIqJSybA2Sn7fPUSPj2Ef29vbPfbn5l1LRERUKmm1dnB0rIi0tLsAAAeHstDrtdDpTD9Do9drzGpvyzHW6ENEkJV1D2lpd+HoWBFaLQsZIiKix8bJqQoAKMWMVquFXm/6rdHmtrflGGv24ehYUdnXj5vZhcz169cRERGBU6dOISoqCo0aNcKmTZuM2gwZMgRHjuT+ToctW7agcePGys+pqamYPXs2du3ahezsbLRv3x7vvvsuatSoYcFQiIiIzKPRaODsXBWVKlUGoIezsyOSk9NNOjNhZ6eBs3N5k9vbcow1+7Czs4dWa70rWcwuZKKiorB//354eXlBr9fne5FUq1atMHnyZKNtbm5uRj+PHz8ely9fxvTp01G2bFl8+umnGDlyJH744QfY2/NkERERFQ2tVgt7e3uUK1cOGRk6kxass7fXmtXelmOKKi9rMLtaCAwMRNeuXQEAU6ZMwZkzZ/Js5+TkBG9v73yf58SJEzh48CAiIiIQEBAAAGjYsCF69eqFHTt2oFevXuamRkRERKWM2ed6HtfpoQMHDsDJyQn+/v7KtkaNGqFZs2Y4cODAY+mDiIiISjarfWh15MgReHt7o2XLlhg8eDCOHj1q9PiVK1fQsGFDaDTG95Q3atQIV65csVZaREREVIJY5UIUX19fBAcHo0GDBoiNjUVERASGDx+Or7/+Gj4+PgCAlJQUVKpUKVess7Nzvh9Xmcre3rg+s7PTGv3fFLYaw7xK71hsNS9LYmw1L0tiTG3/uB7nPmZe1oix1bxMYZVCZuzYsUY/d+rUCX369MGSJUuwYsUKa3Sp0Go1qFy5Qp6POTk5mv18thrDvErvWGw1L0tibDUvS2Is6cOSeO5j6/ZhSYyt5mVJjK3mVZAiuTWofPny6NixI7Zv365sc3Jywu3bt3O1TU5OhrOzs8V96fWClJR0o212dlo4OTkiJSUDOp1pV1bbagzzKr1jsdW8LImx1bwsiTG1vaFdfkyN5z5mXtaIKe68nJwcLT5LU2z3ODdq1AiHDx+GiBhdJ3P16lU0adLkkZ47v9vAdDq92beI2WoM8yq9Y7HVvCyJsdW8LImxpA9L4rmPmZc1Y2w1r4IUyXctpaenY9++fWjZsqWyrUOHDkhOTsbhw4eVbVevXsW5c+fQoUOHokiLiIiIVM7sMzIZGRnYv38/AODmzZtIS0vDtm3bAAB+fn64cuUKVq5ciW7dusHV1RWxsbFYtWoV4uLisHDhQuV5fHx8EBAQgLfffhuTJ09G2bJlsWDBAri7uyMoKOgxDY+IiIhKMrMLmYSEBIwbN85om+Hn1atXo1atWsjOzsaCBQuQlJQER0dH+Pj4YMaMGfD09DSK+/TTTzF79mxMmzYNOTk5CAgIwLvvvstVfYmIiMgkZlcMbm5uuHjxYoFtIiIiTHquSpUqYdasWZg1a5a5aRAREREVzTUyRERERNbAQoaIiIhUi4UMERERqRYLGSIiIlItFjJERESkWixkiIiISLVYyBAREZFqsZAhIiIi1WIhQ0RERKrFQoaIiIhUi4UMERERqRYLGSIiIlItFjJERESkWixkiIiISLVYyBAREZFqsZAhIiIi1WIhQ0RERKrFQoaIiIhUi4UMERERqRYLGSIiIlItFjJERESkWixkiIiISLVYyBAREZFqsZAhIiIi1WIhQ0RERKrFQoaIiIhUi4UMERERqRYLGSIiIlItFjJERESkWixkiIiISLVYyBAREZFqsZAhIiIi1WIhQ0RERKrFQoaIiIhUy764EyCyBq1WA61WAwCws9Ma/V+vF+j1Umy5ERHR48NChkocrVaDKi6O0NjZGW13cnIEAIhOh8SkDBYzREQlAAsZKnG0Ws39IiYiAoiJMX6wdm1oQkOh1WpYyBARlQAsZKjkiokBoqOLOwsiIrIiswuZ69evIyIiAqdOnUJUVBQaNWqETZs2KY+npaVh1apV2L9/P65duwYHBwd4enpiwoQJcHd3V9r9/fff6NKlS67n9/Lywrp16ywcDhEREZUmZhcyUVFR2L9/P7y8vKDX6yFifHr+1q1b+P777/Hss89i/PjxuHfvHr744gsMGjQIP/zwAxo3bmzUfuLEiWjTpo3yc4UKFSwcChEREZU2ZhcygYGB6Nq1KwBgypQpOHPmjNHjbm5u2LlzJxwdHZVtbdu2RWBgIL755htMnTrVqH39+vXh7e1tQepERERU2pldyGi1BS89U758+VzbKlSogHr16iE2Ntbc7oiIiIjyVSQX+6akpCAqKgpPP/10rsemT5+OCRMmwMXFBV26dMGkSZPg4uLySP3Z2xsXWw+vI2IKW41hXoXHmPJ8psTbwljUkJclMbaalyUxprZ/XI9zHzMva8TYal6mKJJC5uOPP4ZGo8Hzzz+vbHNwcMDzzz+PgIAAODk54dSpU1i2bBnOnDmD9evXo0yZMhb1pdVqULly3tfZGNYRMYetxjAv82PMjbfVsdhqXpbE2GpelsQUxTFpST+2ur8siWFepXss+bF6IfPDDz9g3bp1mDNnDmrVqqVsr1GjBqZPn6787OfnhyeffBJhYWHYuXMnevXqZVF/er0gJSXdaJudnRZOTo5IScmATqc36XlsNYZ5FR5jaFMQU+JtYSxqyMuSGFvNy5IYU9sXdlyaGs99zLysEVPceTk5OVp8lsaqhcz+/fsxbdo0jBo1CgMGDCi0fceOHVG+fHmcPXvW4kIGAHJy8t6hOp0+38fyY6sxzMv8GHPjbXUstpqXJTG2mpclMUVxTBZVXrYaw7xK91jyY7UvjTx58iTGjRuH/v37Y9y4cdbqhoiIiEoxqxQyly9fRlhYGNq2bYsZM2aYHLd3716kp6ejZcuW1kiLiIiIShizP1rKyMjA/v37AQA3b95EWloatm3bBuD+dS4igtDQUJQtWxZDhw41WmemYsWKeOKJJwAAc+bMgUajgbe3N5ycnBAZGYnw8HB4eHgo69QQERERFcTsQiYhISHXR0WGn1evXg0AuH37NgBg2LBhRu38/Pzw9ddfAwAaN26Mb7/9FuvWrUNmZiZq1qyJgQMHYuzYsbC351dAERERUeHMrhjc3Nxw8eLFAtsU9jgAhISEICQkxNzuiYiIiBRWu9iXiIiIyNpYyBAREZFqsZAhIiIi1WIhQ0RERKrFQoaIiIhUi4UMERERqRYLGSIiIlItFjJERESkWixkiIiISLVYyBAREZFqsZAhIiIi1WIhQ0RERKrFr5kmVdBqNdBqNbCzu197G/6v1wv0einO1IiIqBixkCGbp9VqUMXFERo7O2Wbk5MjAEB0OiQmZbCYISIqpVjIkM3TajX3i5iICCAm5t8HateGJjQUWq2GhQwRUSnFQobUIyYGiI4u7iyIiMiG8GJfIiIiUi0WMkRERKRaLGSIiIhItVjIEBERkWqxkCEiIiLVYiFDREREqsXbr4mIiGwQVzQ3DQsZIiIiG8MVzU3HQoaIqJTjX/62hyuam46FDBFRKca//G0cVzQvFAsZIqJSjH/5k9qxkCEiIv7lT6rFQoaIiIhMZmvXVLGQISIiIpPY4jVVLGSIiIjIJLZ4TRULGSIiIjKPDV1Txa8oICIiItViIUNERESqxUKGiIiIVIuFDBEREakWCxkiIiJSLRYyREREpFpmFzLXr1/HtGnTEBwcjObNm6NPnz55tlu/fj26d++Oli1bol+/fti7d2+uNqmpqXj77bfh5+cHHx8fjB07FrGxseaPgohUQavVwN5ea7QiqL39/f+0Wk0xZ0dEamR2IRMVFYX9+/ejfv36aNy4cZ5tNm/ejKlTp6Jnz55YsWIFvL298frrr+PkyZNG7caPH49Dhw5h+vTpmDdvHq5evYqRI0ciJyfHosEQke0yrAhauXIFZSVQJ6f7P1euXAFVXBxZzBCR2cxeEC8wMBBdu3YFAEyZMgVnzpzJ1eazzz5D7969MX78eABA27ZtcenSJXz++edYsWIFAODEiRM4ePAgIiIiEBAQAABo2LAhevXqhR07dqBXr16WjomIbFC+K4IC/KZlIrKY2WdktNqCQ6Kjo3Ht2jX07NnTaHuvXr1w+PBhZGVlAQAOHDgAJycn+Pv7K20aNWqEZs2a4cCBA+amRURqYVgR9MH/Hi5siIhM9Ni/ouDKlSsA7p9deVDjxo2RnZ2N6OhoNG7cGFeuXEHDhg2h0RifSm7UqJHyHJaytzcuth7+hk5T2GpMaczL3MdNyaGgNqVxHxdFTGmfl8f1uNrzsiRG7XNvSQyPF9M99kImOTkZAODk5GS03fCz4fGUlBRUqlQpV7yzs3OeH1eZSqvVoHLlCnk+Zvhc3hy2GlPa8yqKPkv7PrbVubTVsRTVcVxS8rIkpiTNva3Oi63mVZAS96WRer0gJSXdaJudnRZOTo5IScmATqc36XlsNaY05mVol5+H4wtrn1eMJXkVdYyt5mVqTGmfF3OP45KalyUxap97S2JK2/Hi5ORo8Vmax17IODs7A7h/a3X16tWV7SkpKUaPOzk54fbt27nik5OTlTaWysnJeyfqdPp8H8uPrcaU9ryKos/Svo9tdS5tdSxFdRyXlLwsiSlJc2+r82KreRXksS+I16hRIwDIdZ3LlStXUKZMGdStW1dpd/XqVYgY36Fw9epV5TmIiIiICvLYC5m6deuiQYMG2LZtm9H2LVu2oF27dnBwcAAAdOjQAcnJyTh8+LDS5urVqzh37hw6dOjwuNMiIiKiEsjsj5YyMjKwf/9+AMDNmzeRlpamFC1+fn6oUqUKxowZg0mTJqFevXpo06YNtmzZgsjISKxZs0Z5Hh8fHwQEBODtt9/G5MmTUbZsWSxYsADu7u4ICgp6TMMjIiqcVqtRFuN7+K4KvV64tg2RDTO7kElISMC4ceOMthl+Xr16Ndq0aYM+ffogIyMDK1aswPLly9GwYUMsXrwYPj4+RnGffvopZs+ejWnTpiEnJwcBAQF49913YW9f4q5BJiIbZVhxWGNnZ7TdcEGj6HRITMpgMUNko8yuGNzc3HDx4sVC24WEhCAkJKTANpUqVcKsWbMwa9Ysc9MgInosuOIwkbrx1AcREfDvisNEpCqP/WJfIiIioqLCQoaIiIhUi4UMERERqRYLGSIiIlItFjJERESkWixkiIiISLVYyBAREZFqsZAhIiIi1WIhQ0RERKrFQoaIiIhUi4UMERERqRYLGSIiIlItFjJERESkWixkiIiISLVYyBAREZFqsZAhIiIi1WIhQ0RERKrFQoaIiIhUi4UMERERqRYLGSIiIlItFjJERESkWixkiIiISLVYyBAREZFqsZAhIiIi1WIhQ0RERKrFQoaIiIhUi4UMERERqRYLGSIiIlItFjJERESkWixkiIiISLVYyBAREZFqsZAhIiIi1WIhQ0RERKrFQoaIiIhUi4UMERERqRYLGSIiIlItFjJERESkWvbWeNIhQ4bgyJEjeT42f/589O7dO982W7ZsQePGja2RFpEqabUaaLUa2Nnd/7vD8H8A0OsFer0UV2pERMXOKoXMe++9h7S0NKNtX331FXbs2IF27dop21q1aoXJkycbtXNzc7NGSkSqpNVqUMXFERo7O2Wbk5Oj8m/R6ZCYlMFihohKLasUMk888USubW+88Qb8/f1RpUoVZZuTkxO8vb2tkQJRiaDVau4XMRERQEyM8YO1a0MTGgqtVsNChohKLasUMg/7888/8ffff2P8+PFF0R1RyRMTA0RHF3cWREQ2p0gKmU2bNqF8+fLo0qWL0fYjR47A29sbOp0OXl5eGDduHHx9fR+5P3t742uY87q2oDC2GlMa8zL3cVNyKKiNLe1jjqXk5PW4Hn/cr8mizsuSGFs6jouqDx4vprN6IZOTk4OtW7ciMDAQ5cuXV7b7+voiODgYDRo0QGxsLCIiIjB8+HB8/fXX8PHxsbg/rVaDypUr5PnYg9cWmMpWY0p7XkXRp63uY0viORbbzMuS+KJ4TVoSX5LeX2w1L0viS9Lxkh+rFzKHDh1CYmIi+vTpY7R97NixRj936tQJffr0wZIlS7BixQqL+9PrBSkp6Ubb7Oy0cHJyREpKBnQ6vUnPY6sxpTEvQ7v8PBxfWPu8YizJqyhiOJaSk5e5x7Gl/dh6XpbE2NJxXFR9lLbjxcnJ0eKzNFYvZDZt2gQXFxcEBAQU2K58+fLo2LEjtm/f/sh95uTkvRN1On2+j+XHVmNKe15F0aet7mNL4jkW28zLkviieE0WRV6WxNjqcWyrx6Ql/dhqXgWx6oJ4mZmZ2LVrF3r06IEyZcpYsysiIiIqhaxayOzZswfp6eno27dvoW3T09Oxb98+tGzZ0popERERUQli1Y+WfvnlF9SpUwdPPfWU0fZjx45h5cqV6NatG1xdXREbG4tVq1YhLi4OCxcufGz9c0VUIiKiks1qhUxycjJ+/fVXDB06FBqNxuix6tWrIzs7GwsWLEBSUhIcHR3h4+ODGTNmwNPT87H0zxVRiYiISj6rFTLOzs44c+ZMno/Vr18fERER1uoaAFdEJSIiKg2KZEG8YsUVUYmIiEosq17sS0RERGRNLGSIiIhItVjIEBERkWqxkCEiIiLVYiFDREREqsVChoiIiFSLhQwRERGpFgsZIiIiUi0WMkRERKRaLGSIiIhItVjIEBERkWqV/O9aql3btG1ERESkOiW6kBG9HprQ0HwfIyIiInUr0YWMRqvFRhxBPFKNtldDJfTX+uUZo9VqoNVqYGd3/1M3w//1eoFeL9ZNmIiIiMxSogsZADiDaEQjwWhbXVRFf+QuZLRaDaq4OEJjZ6dsc3JyBACITofEpAwWM0RERDakxBcy5tBqNfeLmIgIICbm3wdq14YmNBRarYaFDBERkQ1hIZOXmBggOrq4syAiIqJCsJAhohKH17oRlR4sZIioROG1bkSlCwsZIipReK0bUenCQoaISiZe60ZUKvArCoiIiEi1WMgQERGRarGQISIiItViIUNERESqxUKGiIiIVIuFDBEREakWb78mIiKbxBWayRQsZIiIyOZwhWYyFQsZIiKyOVyhmUzFQoaIiGwXV2imQvBiXyIiIlItFjJERESkWixkiIiISLVYyBAREZFqsZAhIiIi1WIhQ0RERKpllULmxx9/hLu7e67/5s2bZ9Ru/fr16N69O1q2bIl+/fph79691kiHyCRarQb29lqjVUTt7e//p9Vqijk7IqKCGd7D8nofK8nvYVZdR2blypWoVKmS8nPNmjWVf2/evBlTp07Fq6++irZt22LLli14/fXXsXbtWnh7e1szLaJcClpFFOBKokRk2/J6DwNKx2rIVi1kWrRogSpVquT52GeffYbevXtj/PjxAIC2bdvi0qVL+Pzzz7FixQprpkWUS76riAJcSZSIbF5pfg8rlpV9o6Ojce3aNfz3v/812t6rVy/MnTsXWVlZcHBwKI7UqLTjKqJEpGal8D3MqoVMnz59cPfuXdSpUwf/+c9/MGLECNjZ2eHKlSsAgIYNGxq1b9y4MbKzsxEdHY3GjRtb3O+Dnw8W5OE2hcWY+rgpfVsaUxR92Fpe5j5ujbkvrI21xm+reVkSU1RjKYrjpSjysrQfW8/L1Bhbzauo+uBxbDqrFDLVq1fHmDFj4OXlBY1Ggz179uDTTz/FnTt3MG3aNCQnJwMAnJycjOIMPxset4RWq0HlyhVMavvgNRCPs725z2vNXIo6pqjyKo4+TYmx1fHb0j561HhbPV6KKq+ieE1aEl/Ux4st5WWrrxVLYmz5eMmPVQqZ9u3bo3379srPAQEBKFu2LL766iu8+uqr1uhSodcLUlLSYWenLXRHpaRkQKfTKz8XFvNw+4cZ4gtr9ygxRdGHreVl7rxYY+7ziskrx8c9flvNy5KYohpLURwvRZGXpf3Yel6mxthqXkXVR2k7jp2cHC0+S1Nk18j07NkTX3zxBc6fPw9nZ2cAQGpqKqpXr660SUlJAQDlcUvl5Jh2QOl0epPbmtPe3Oe1Zi4lNa/i6NOUGFsdvy3to0eNt9XjpajyKorXZFHkZWmMLeZlq68VS2Js+XjJT7EsiNeoUSMAUK6VMbhy5QrKlCmDunXrFkdaREREpDJFVshs2bIFdnZ2aN68OerWrYsGDRpg27Ztudq0a9eOdywRERGRSazy0VJoaCjatGkDd3d3AMDu3buxbt06vPTSS8pHSWPGjMGkSZNQr149tGnTBlu2bEFkZCTWrFljjZSIiIioBLJKIdOwYUP88MMPuH37NvR6PRo0aIC3334bQ4YMUdr06dMHGRkZWLFiBZYvX46GDRti8eLF8PHxsUZKREREVAJZpZB59913TWoXEhKCkJAQa6RAREREpQC//ZqIiIhUi4UMERERqRYLGSIiIlKtYvnSSCKyPVqtBlqtJtd3oej1UiK/MZeISgYWMkQErVaDKi6O0NjZKdsMy5CLTofEpAwWM0Rkk1jIEBG0Ws39IiYiAoiJ+feB2rWhCQ2FVqthIUNENomFDBH9KyYGiI4u7iyIiEzGi32JiIhItVjIEBERkWqxkCEiIiLVYiFDREREqsVChoiIiFSLhQwRERGpFgsZIiIiUi0WMkRERKRaLGSIiIhItVjIEBERkWqxkCEiIiLVYiFDREREqsVChoiIiFSLhQwRERGpFgsZIiIiUi374k6AiKggWq0GWq0Gdnb3/+4y/F+vF+j1UpypEZENYCFDRDZLq9WgiosjNHZ2yjYnJ0cAgOh0SEzKYDFDVMqxkCEim6XVau4XMRERQEzMvw/Urg1NaCi0Wg0LGaJSjoUMEdm+mBggOrq4syAiG8SLfYmIiEi1WMgQERGRarGQISIiItViIUNERESqxUKGiIiIVIuFDBEREakWCxkiIiJSLRYyREREpFosZIiIiEi1WMgQERGRarGQISIiItViIUNERESqZZUvjdy6dSt+/vlnnD17FikpKahfvz6GDBmCZ599FhqNBgAwZMgQHDlyJFfsli1b0LhxY2ukRURERCWMVQqZL7/8Eq6urpgyZQoqV66M3377DVOnTsXt27fx+uuvK+1atWqFyZMnG8W6ublZIyUiIiIqgaxSyCxduhRVqlRRfm7Xrh2SkpKwatUqjBo1Clrt/U+0nJyc4O3tbY0UiIiIqBSwyjUyDxYxBs2aNUNaWhrS09Ot0SURERGVQlY5I5OX48ePo2bNmqhYsaKy7ciRI/D29oZOp4OXlxfGjRsHX1/fR+7L3l4LO7vCa7SH2xQWY+rjpvRtaUxR9GFreZn7uDXmvrA21hp/UeVVFMd+Ub0mi+J4yesxW9jHasjL1Bhbzauo+uBxbLoiKWSOHTuGLVu2GF0P4+vri+DgYDRo0ACxsbGIiIjA8OHD8fXXX8PHx8fivrRaDSpXrmBSWycnR7Oe29T25j6vNXMp6piiyqs4+jQlxlbHX1T7uKjnUu1zb0l8UewjS+KL+ti3pbxs9XVvSYwtHy/5sXohc/v2bUyYMAFt2rTBSy+9pGwfO3asUbtOnTqhT58+WLJkCVasWGFxf3q9ICUlHXZ22kJ3VEpKBnQ6vfJzYTEPt3+YIb6wdo8SY+0+NBoNtNr7/1WsWA5paZnQ6wV6vUBEiiUvc+fFGnOfV0xeOT7u8RdVXkVx7BfVa7Iojpe8+rOFfayGvEyNsdW8iqqP0nYcOzk5WnyWxqqFTEpKCkaOHAkXFxcsWrRIucg3L+XLl0fHjh2xffv2R+43J8e0A0qn05vc1pz25j6vNXMxJ0ar1aCKSzlo7OyUbRUrlgMAiE6HxKQM6PX5FzPWyssa8daKsdXxF9U+Luq5VPvcWxJfFPuoKPKyNMYW87LV170lMbZ8vOTHaoVMZmYmwsLCkJqaiu+//x6VKlWyVlf0mGi1mvtFTEQEEBPz7wO1a0MTGgqtVlNoIUNERFSUrFLI5OTkYPz48bhy5QrWrl2LmjVrFhqTnp6Offv2oWXLltZIicwREwNERxd3FkRERIWySiEzY8YM7N27F1OmTEFaWhpOnjypPNa8eXNERkZi5cqV6NatG1xdXREbG4tVq1YhLi4OCxcutEZKNsVwDQqQ+wpuw/UoRI/CcIzx+CKigpSE9wqrFDKHDh0CAMyZMyfXY7t370b16tWRnZ2NBQsWICkpCY6OjvDx8cGMGTPg6elpjZRsxv3rUByNrkMB/r2C29RrUYjyk9cxxuOLiB5WUt4rrFLI7Nmzp9A2ERER1uja5uV7HQrAa1HoseC1TkRkipLyXlFkC+LRQ3gdClkbjzEiMoXK3ytYyJRgJeGzTyIqGXhtIFkLC5kSqqR89klE6sdrA8maWMiUUCXls08iUj9eG0jWxEKmpFP5Z59EVILw/YisgIUM0SPgdUhERMWLhQyRhXgdEhFR8WMh8xjwr/LSidchkbXZ8p0+fN8jW8FC5hHxr3Li5/5kDbZ8pw/f98iWsJB5RPyrnIiswZbv9OH7HtkSFjKPC/8qJyJrsOX3FlvOjUoNbXEnQERERGQpFjJERESkWvxoiYgsYst31BBR6cFChojMZst31BBR6cJChojMZst31BBR6cJChogsx7tWiKiY8WJfIiIiUi0WMkRERKRaLGSIiIhItVjIEBERkWrxYl96JPl9Ay7AtUSISB34Td7qxkKGLFbQN+ACXEuEiGwfv8lb/VjIkMW4lgiR7eFZUvNY8k3e3Me2hYUMPTquJUJkE3iW9BGY+D7GfWx7WMgQEZUQPEtqfdzHtoeFDBFRScOzpNbHfWwzePs1ERERqRbPyBARUYnBW6lLHxYyRERUIvBW6tKJhYxKlKS/MkrSWKj04nFseyy5lZrUj4WMCpSkvzJK0lio9OJxbON4IW6pwkJGBUrSXxklaSyW4l/y6sfjmMh2sJBRk5L0V0ZJGosZ+Jd8CVNKj2MiW8JChqgI8S95otKJZ2Kth4UMUXHgX/JEpQbPxFoXCxkiIiIr4plY62IhQ0REVBR4JtYqivUrCv766y8MHz4c3t7e8Pf3x9y5c5GVlVWcKREREZGKFNsZmeTkZAwdOhQNGjTAokWLcOfOHcyZMweZmZmYNm1acaVFREREKlJshcx3332Hf/75B4sXL4aLiwsAQKfTYcaMGQgLC0PNmjWLKzWgdu2Cf1aTkjQWIiJSJWvetVVshcyBAwfQrl07pYgBgJ49e+K9997DoUOH8MwzzxRLXqLXQxMamud2tSlJYyEiInUy5a6tR6ERkWK5VLpdu3Z49tlnMWnSJKPt7du3R3BwcK7tphK5X91pNIBWq0UKMqCD8S9uO2jhBEfo9Xo8OHpDTAayoMe/D2ihgSMccrV/MAYpKYBO90AndoCTU7595GpvSUw+7UvqWIolr5I0FlvNqySNxVbzKkljeYx5laSx2GpeRjHp6bljypeHXq+HRqOBRqOBJYrtjExKSgqcnJxybXd2dkZycrLFz6vRaGBn9+/OcIJjvm212ryvdXaEg1nt73eUeywFxuTT3pKYgvIqSWMpzrwsibHVsdhqXpbE2OpYbDUvS2JsdSyPNS9LYmx1LLaaFwCUL29+jAmK9a4lIiIiokdRbIWMk5MTUlNTc21PTk6Gs7NzMWREREREalNshUyjRo1w5coVo22pqamIi4tDo0aNiikrIiIiUpNiK2Q6dOiA3377DSkpKcq2bdu2QavVwt/fv7jSIiIiIhUptruWkpOT0bt3bzRs2BBhYWHKgnh9+/blgnhERERkkmIrZID7X1HwwQcf4MSJE6hQoQKCg4MxYcIEODjkfacNERER0YOKtZAhIiIiehS8/ZqIiIhUi4UMERERqRYLGSIiIlItFjJERESkWixkiIiISLVYyBAREZFqsZAhIiIi1WIhUwKZuzQQlxIiIiK1YiHzmOj1erPam1I83LlzBxkZGWbnotForNr+zz//RGZmplkxxcUWizQRscm8LGHJOCwdv7kx5r4mi4KI2GRelrBkDvV6PXQ6ndkx5ijKfWzOPhARs8duqyzZv5bMvalKZCFz/PhxHD9+HCdOnMC5c+eQmppaYHtLD7ALFy7g2rVrAACttuBdmZOTg23btuGPP/5Aenq6Ujzk90LIysrCgAED8M4772Djxo24fft2rrbp6em5+li1apXRF3EaYvLqJzs7G5MnT8b69etNPjCzsrLw6quvYsaMGbhz506BY3hQYmIivvzyS/z444+4dOlSrvzyEhkZiZMnT+LUqVO4cOEC0tLSTMrxQeYWaUVBo9GYnZdOp7Pqm3N8fLxZr4EDBw4gKyvL5HE8OM+WjN8QZ47CXpPFQaPRmJ2XNec+v3kv6HX5KHOv1WphZ2dnVo7m7i9L9rGlCnsff/i4N2XsD8aYM/f37t0zqZ3BzZs3kZOTk2/feY1p8+bNSE5ONnn/Pvj7x5K5N5W9VZ61mJw7dw4rV67E4cOHcffuXdjb26Nhw4Zo1KgRfHx88PTTT+OJJ54wmoR79+6hbNmyyg42HDQFTVRMTAzWrFmDjRs3IiEhAa6urhg1ahSCg4Oh1WpzxZ49exZLly7Fvn37kJOTgzp16mDu3Llo3bo1NBoN0tPTjXIA7hdjiYmJ2Lt3L/bu3YsyZcqgU6dO6N27N7y8vODi4oKXX34Z48ePR9u2bQEA33zzDTZs2ICQkBDleTQajTLGrKwso++x2rhxI44ePQp/f38l5+TkZMTFxSEqKgpVq1aFp6cnypUrZxSTkpKCPXv2IDY2FlOmTMGTTz5Z4LwcOXIECxYswOnTp2Fvb4+yZcviww8/RNeuXaHRaHD37l1UqlQJ9vb3D8dLly7hiy++wIEDB5CYmAh7e3vUqlULzZs3x1NPPQV/f3888cQT0Ov1ec5TUlISbty4gRMnTsDNzQ0eHh5wdnZWxiEi+b4JF/TYw+7du4ebN2/iypUrqF+/fqH7ITY2FkePHsXt27fh6+sLT0/PAvv+559/cP78ebRu3dro2NDpdNBqtXnmmZiYiM2bN2PQoEH5fmfZw/vt7t27mDt3Lpo3b46hQ4cWOv7Y2Fi88sorCAoKwoQJE9CwYcMC2xvG9tdff2HTpk1ITk5GUFAQ2rVrV+j+Tk1Nxd9//40TJ07A1dUVTZs2RaVKlVCuXDlotdpc8YXNvV6vz7eQMnXuzZ13oPC5f3hOzJ37xz3v+e2Hopr7/Obd0dERGo0mz3m8c+cOTp06hRMnTqBBgwZ44oknUKNGDVSvXt3oPcyUfVOQtLQ0nD17FlFRUfDw8IC3t3eBx010dDS2bt2K2NhYdOnSpdCxp6Wl4c8//0THjh2N5j4nJyfP3y/A/YL0q6++QlhYGCpWrFjoGBMTEzFt2jR4enpizJgxyvaCjoE7d+7gjTfeQIsWLTBlyhT4+voCKPh1o9PpcPbsWaxZswbp6ekIDg5GUFCQWe+zpihRhcysWbPg4OCAiRMnokOHDrhx4wZ2796NY8eO4cSJE9ixYwcGDx6MXr16KTH//e9/kZOTg379+qFjx45wdHRUHtPpdHlW93PmzMHNmzcRHByMJk2aYOfOnViwYAFq1aoFf3//XC+KBQsWQKfT4YMPPkCzZs3w4YcfYteuXbCzs0N4eDhEBN7e3ggODkadOnUgImjXrh1ef/11nDp1Ci+//DJOnz6Nn3/+Gb/88gvc3Nzg7u6Os2fPGh2069evR/v27ZUxxMXFYdu2bfjpp5/wzz//wNvbG/369YO/vz8A4Ntvv0WPHj3QvXt3AMDBgwexcuVK/P7773B2dkb16tXh5uaGl19+GX5+fgCA1atX48UXX4S7uzs++eQThIWF4Z133kHnzp2h1WrzfENYtGgRqlWrhpUrV8LDwwNTp07Frl274OjoiCVLlkCj0aBly5YYMGAAmjRpgtmzZyMzMxNhYWHw8/PDpUuX8OOPP2LHjh04efIkDh48iLCwMLRu3TrXMXD48GGsWLECv/32G9zc3BAXFwe9Xg8PDw/06dMHPXv2RJUqVYxi7ty5gzJlyqBKlSpGL678Xmx6vR5RUVFYuXIlfvnlF7i4uMDV1RUvvPACnn322bwOTRw6dAhLly7FsWPHUKdOHWzevBmzZs1C06ZNkZ6ejvLlyxv9dafRaBAREYElS5bA29sbbdq0Qc+ePdG0aVPlzS07OxvR0dGoV6+eUgQuWbIEe/fuxcCBA436T05Oxj///IM6derkmp81a9bg4sWLeOGFF6DRaCAiuHv3Lvbu3QtHR0e4urqiTp06qF69OkQE3333HTQaDQ4ePIjY2FhMmzYNzZs3L3Cfbd++HUuWLMHt27dRq1Yt7Nu3D++//z7at2+P1NRUVKpUKdd+P3bsGFasWIH9+/ejWrVqiI+Ph6OjI9q2bYugoCAEBQWhQoUKRnO/cuVKHDp0yGpzf+HCBURERJg87yKCw4cPY8mSJQXOvWFOzJ37+vXrw87OzuJ5v3DhgsnzrtFoHtvcz5gxAx06dMhz7o8fP46VK1di3759Js07AOzZswfh4eG4cOECGjRogB9//BEpKSmoV68eunTpgl69esHDw8Mo5tq1ayhTpgxcXV2N9k1+RY1er8fp06exfPly7N69G9WqVYODgwMGDBiAMWPG5Dn/u3fvxpIlS3D16lW4urpi165dmDlzJgICApCUlKS8f9vb2yv7Lzw8HCtXrkSNGjXw9NNP47nnnoO3t7fyGs/KysLp06fRsmVLpWhdvnw59u3bh9dee81oX964cQM6nQ6NGjUyGtOaNWuQmJiIrl27QqvVQqfT4ebNm9i2bRu0Wi3q1KmDxo0b48knn1QKxu+++w6Ojo5ISEjA22+/jenTp8Pf37/AgmTz5s1YsmQJsrOzUaNGDUyePBnJyckICQlBXFwcHBwcoNVqUalSpUcqbkrMl0bGxcWhW7duWL16dZ5/6e7fvx9fffUVDh8+jGHDhmHChAlITU1FQEAAatasCQCoVKkSfH190aNHD7Rp08boOVJSUnD48GFUrVoVI0aMwKJFi9C+fXsA9yvuadOm4fr169iwYYPRm+WePXswduxYfPHFF0oxsHfvXsydOxcZGRl48skn8c8//+DEiRPw8/PDggULlPibN29i8uTJqFevHmbNmoWMjAycPHkSBw4cwHfffYfMzEy0aNECgYGBCAgIwH/+8x+sW7cOHh4e0Gq1mDhxIn799Vd4enqiVq1aiIyMRFRUFEJDQxEaGorhw4cjLCxMKey6d++OmjVrYvTo0dBoNPj999/x888/w97eHsuWLUO5cuXQqVMnbNy4EU2bNsXFixcxffp0REdHY/z48bneRIH7f8F1794dX331lTIvp0+fxuuvvw6tVotWrVohLS0NR48ehZubG6ZPn46XXnoJX375pVGhEhcXh7CwMOXAP3XqFObNm4eePXsa9Wd4wx8yZAicnJyQlZWFy5cvY+fOnTh48CAcHBwQGhqKF198UXkzHDNmDCpUqAB/f380b94crq6uRn/B5fUCe+mll3Dv3j0MHToUer0eP/zwA37//XfMmzcPvXv3zhXzzDPPwM3NTfnLd9q0aXj66afh7e2N9evXIyoqCj169EBYWBiqV68O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\n",
"text/plain": [
"<Figure size 640x480 with 1 Axes>"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"def classes_plot(y_val,y_pred):\n",
" vd = pd.DataFrame([y_pred,y_val],index=['pred','real']).T\n",
" vd_pred_true = vd[vd.pred==vd.real].groupby(by='real').count()\n",
" vd_pred_all = vd.groupby(by='real').count()\n",
" vd_pred = pd.concat([vd_pred_true,vd_pred_all-vd_pred_true],axis=1)\n",
" # vd_pred.false[vd_pred.isna().iloc[:,0]]=vd.real[vd_pred.isna().iloc[:,0]].values\n",
" vd_pred.columns = ['true','false']\n",
" #print(vd_pred_all.pred[vd_pred.false.isna().values])\n",
" #print(vd_pred_true.pred[vd_pred_true[vd_pred.false.isna()]])\n",
" vd_pred.false[vd_pred.false.isna()]=vd_pred_all.pred[vd_pred.false.isna().values]\n",
" vd_pred = vd_pred.fillna(0)\n",
" vd_pred_sum = vd_pred.sum()\n",
" print(vd_pred_sum.true/(vd_pred_sum.true+vd_pred_sum.false))\n",
" return vd_pred.plot(kind='bar',stacked=True,color=['#66FF99','#ff6666'],rot=70)\n",
"\n",
"classes_plot(y_val, y_pred)"
]
},
{
"cell_type": "code",
"execution_count": 49,
"id": "78fc9075-6f7f-442a-addc-42eee1a6d83e",
"metadata": {},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"0.6523235800344234\n"
]
},
{
"data": {
"text/plain": [
"<AxesSubplot:xlabel='real'>"
]
},
"execution_count": 49,
"metadata": {},
"output_type": "execute_result"
},
{
"data": {
"image/png": "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T8fevXvRsmVLZVn79u2RnJyMQ4cOKcuuXLmCs2fPon379rZIi4iIiOyc2WdkMjIysG/fPgDAjRs3kJaWhq1btwIAAgICcPnyZSxfvhxdu3aFu7s74uLisGLFCsTHx2P+/PnK+/j5+SE4OBhvv/02Jk6ciLJly2Lu3Lnw9PREaGhoETWPiIiISjKzC5nExESMGTPGaJnh55UrV6JWrVrIzs7G3LlzcffuXTg7O8PPzw/Tpk2Dt7e3Udy8efMwc+ZMTJkyBTk5OQgODsa7777LWX2JiIjIJGZXDB4eHrhw4UKB60RFRZn0XpUqVcKMGTMwY8YMc9MgIiIiss0YGSIiIiJrYCFDREREdouFDBEREdktFjJERERkt1jIEBERkd1iIUNERER2i4UMERER2S0WMkRERGS3WMgQERGR3WIhQ0RERHaLhQwRERHZLRYyREREZLdYyBAREZHdYiFDREREdouFDBEREdktFjJERERkt1jIEBERkd1iIUNERER2i4UMERER2S0WMkRERGS3WMgQERGR3WIhQ0RERHaLhQwRERHZLRYyREREZLdYyBAREZHdYiFDREREdouFDBEREdktFjJERERkt1jIEBERkd1iIUNERER2i4UMERER2S0WMkRERGS3WMgQERGR3WIhQ0RERHbLsbgTILIGrVYDrVYDAHBw0Br9X68X6PVSbLkREVHRYSFDJY5Wq0EVN2doHByMlru4OAMARKdD0t0MFjNERCUACxkqcbRazf0iJioKiI01frF2bWgiIqDValjIEBGVACxkqOSKjQViYoo7CyIisiKzC5lr164hKioKJ06cQHR0NBo1aoSNGzcqr6elpWHFihXYt28frl69CicnJ3h7e2PcuHHw9PRU1vv777/RuXPnXO/v4+ODNWvWWNgcIiIiKk3MLmSio6Oxb98++Pj4QK/XQ8T49PzNmzfx/fff45lnnsHYsWNx7949fPHFFxgwYADWr1+Pxo0bG60/fvx4tGnTRvm5QoUKFjaFiIiIShuzC5mQkBB06dIFADBp0iScPn3a6HUPDw/s2LEDzs7OyrLAwECEhITgm2++weTJk43Wr1+/Pnx9fS1InYiIiEo7swsZrbbgqWfKly+fa1mFChVQr149xMXFmbs5IiIionzZZLBvSkoKoqOj8eSTT+Z6berUqRg3bhzc3NzQuXNnTJgwAW5u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\n",
"text/plain": [
"<Figure size 640x480 with 1 Axes>"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"#fit svc\n",
"\n",
"import numpy as np\n",
"from sklearn.pipeline import make_pipeline\n",
"from sklearn.preprocessing import StandardScaler\n",
"from sklearn.metrics import f1_score\n",
"\n",
"from sklearn.svm import SVC\n",
"clf = make_pipeline(StandardScaler(),\n",
" SVC(gamma='auto'))\n",
"clf.fit(X_data, y_data)\n",
"y_pred = clf.predict(X_val)\n",
"classes_plot(y_val, y_pred)"
]
},
{
"cell_type": "code",
"execution_count": 36,
"id": "2e8eeba1-44d6-4036-8413-785cc99bc9c9",
"metadata": {},
"outputs": [],
"source": [
"#fit random_forest\n",
"\n",
"import numpy as np\n",
"from sklearn.pipeline import make_pipeline\n",
"from sklearn.ensemble import RandomForestClassifier\n",
"from sklearn.metrics import f1_score\n",
"\n",
"from sklearn.svm import SVC\n",
"clf = make_pipeline(RandomForestClassifier(n_jobs=-1))\n",
"clf.fit(X_data, y_data)\n",
"y_pred = clf.predict(X_val)\n",
"classes_plot(y_val, y_pred)"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "2cc2f449-c297-4294-a03e-235d76a5ad7f",
"metadata": {},
"outputs": [],
"source": [
"#fit Linear SVC\n",
"\n",
"\n",
"from sklearn.pipeline import make_pipeline\n",
"from sklearn.naive_bayes import MultinomialNB, ComplementNB\n",
"from sklearn.metrics import f1_score\n",
"\n",
"from sklearn.svm import LinearSVC\n",
"clf = make_pipeline(LinearSVC(C=1000, penalty='l1', max_iter=500, dual=False))\n",
"clf.fit(X_data, y_data)\n",
"y_pred = clf.predict(X_val)\n",
"classes_plot(y_val, y_pred)"
]
}
],
"metadata": {
"kernelspec": {
"display_name": "hack",
"language": "python",
"name": "hack"
},
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.8.10"
}
},
"nbformat": 4,
"nbformat_minor": 5
}