{"cells":[{"metadata":{"_uuid":"8f2839f25d086af736a60e9eeb907d3b93b6e0e5","_cell_guid":"b1076dfc-b9ad-4769-8c92-a6c4dae69d19","trusted":true},"cell_type":"code","source":"# This Python 3 environment comes with many helpful analytics libraries installed\n# It is defined by the kaggle/python Docker image: https://github.com/kaggle/docker-python\n# For example, here's several helpful packages to load\n\nimport numpy as np # linear algebra\nimport pandas as pd # data processing, CSV file I/O (e.g. pd.read_csv)\nfrom transformers import AutoTokenizer, AutoModel\nimport tensorflow as tf\nimport transformers\nimport time\n\n\n# Input data files are available in the read-only \"../input/\" directory\n# For example, running this (by clicking run or pressing Shift+Enter) will list all files under the input directory\n\nimport os\nfor dirname, _, filenames in os.walk('/kaggle/input'):\n    for filename in filenames:\n        print(os.path.join(dirname, filename))\n\n# You can write up to 5GB to the current directory (/kaggle/working/) that gets preserved as output when you create a version using \"Save & Run All\" \n# You can also write temporary files to /kaggle/temp/, but they won't be saved outside of the current session","execution_count":null,"outputs":[]},{"metadata":{},"cell_type":"markdown","source":"Проведем тесты на 3 моделях, которые могут работать с мультиязыковыми моделями:\n\n1) Берт , обученный на 100 языках\n\n2)XLM\n\n3) XLM-Roberta","execution_count":null},{"metadata":{},"cell_type":"markdown","source":"BERT\n\nЭто трансформер , состоящий из некоторого количества Encoder слоев в зависимости от конфигурации(12 или 24). Каждый энкодер слой состоит из настаканных multi-head attention с Dropout, LayerNorm и FeedForward слоями внутри.\n\nБерт обучается на следующих задачах:\n\n1) Предсказание замаскированных слов в документе на основе остальных (MLM)\n\n2) Предсказание одного предложения в документе на основе предыдущего (NSP)\n\nНа вход в модель данные должны быть конвертированы в индексы из словаря токенайзера для конкретной конфигурации модели, после чего по каждому индексу достается эмбединг токена, который поэлементно суммируется с векторными представлениями позиции токена в предложении и токена места предложения в документе.\n\nНа выход Берт для одного документа возвращает матрицу размером max_len x embed_size, где по строчкам эмбединги каждого из токенов документа. В первом ряду этой матрицы находится эмбединг так называемого cls токена, который авторы модели советуют использовать как эмбединг всего документа, хотя это и не единственный возможный способ и не всегда самый эффективный.\n\n\nXLM\n\nЭто модель тоже основанная архитектуре берта. Только эта модель отличается тем, что она лучше адаптирована для межязыковых задач. Это возможно засчет отчасти других подходов к обучению. А именно модель обучалась с задачами:\n\n1) Предсказание слова в предложении на основе всех предыдущих (CLM)\n\n2) Предсказание замаскированных слов предложения на основе всех остальных (MLM)\n\n3) Предсказание замаскированных слов на основе предыдущих, только за тем исключением, что входные данные представляются из себя конкатенацию одного и того предложения но на двух языках (TLM)\n\nЭти методы обучения были взяты за основу в следующей модели - забустченной XLM модели на основе берта - XLM-Roberta\n\n\nXLM-Roberta \n\nЭта модель повторяет архитектуру Берта, но как пишут ее создатели , она превосходит сильно результаты берта на межязыковых задачах (спойлер это реально так). Лучшее качество удалось получить за счет измененного процесса обучения, а именно: модель обучалась на следующих задачах:\n\n1) Предсказание слова в предложении на основе всех предыдущих (CLM)\n\n2) Предсказание замаскированных слов предложения на основе всех остальных (MLM)\n\n3) Предсказание замаскированных слов на основе предыдущих, только за тем исключением, что входные данные представляются из себя конкатенацию одного и того предложения но на двух языках (TLM)\n\nНо кроме этого для обучения было собрано 2.5Т данных, и модель обучалась на большем learning rate, batch size, и с большим количеством эпох - как это делалось в Roberta - дообученной версии берта. Таким образом XLM-R это дообученный берт, который обучался на межязыковых данных и с задачами способствующими межязыковому понимаю языка.\n","execution_count":null},{"metadata":{"_uuid":"d629ff2d2480ee46fbb7e2d37f6b5fab8052498a","_cell_guid":"79c7e3d0-c299-4dcb-8224-4455121ee9b0","trusted":true},"cell_type":"code","source":"bert_checkpoint = \"bert-base-multilingual-cased\" #12-layer, 768-hidden, 12-heads, 110M parameters.\nxlm_checkpoint = \"xlm-mlm-100-1280\"\nxlm_roberta_checkpoint = \"xlm-roberta-base\" #~125M parameters with 12-layers, 768-hidden-state, 3072 feed-forward hidden-state, 8-heads\n","execution_count":null,"outputs":[]},{"metadata":{},"cell_type":"markdown","source":"Возьмем часть данных - датасет с первого соревнования Jigsaw, заенкодим их к длине в 128 токенов и запустим 3 модели на одной эпохе, различающихся только трансформером, создающем ембединги входящих текстовых данных, чтобы посмотреть какая из моделей даст лучшее качество на валидационной выборке при прочих равных.","execution_count":null},{"metadata":{"trusted":true},"cell_type":"code","source":"max_len = 128","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"bert_tokenizer = AutoTokenizer.from_pretrained(bert_checkpoint)\nxlm_tokenizer = AutoTokenizer.from_pretrained(xlm_checkpoint)\nxlm_roberta_tokenizer = AutoTokenizer.from_pretrained(xlm_roberta_checkpoint)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"#создадим функцию токенизации датасета\ndef encode_comments(dataframe, tokenizer, max_len=max_len):\n    pos = 0\n    start = time.time()\n    \n    while pos < len(dataframe):\n        temp = dataframe[pos:pos+10000].copy()\n        res = tokenizer.batch_encode_plus(temp.comment_text.values,\n                                          pad_to_max_length=True,\n                                          max_length = max_len,\n                                          return_attention_masks = False\n                                         )\n        if pos == 0:\n            ids = np.array(res[\"input_ids\"])\n            labels = temp.toxic.values\n        else:\n            ids = np.concatenate((ids, np.array(res[\"input_ids\"])))\n            labels = np.concatenate((labels, temp.toxic.values))\n        pos+=10000\n        print(\"Processed\", pos, \"elements\")\n    return ids, labels","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"def make_model(transformer):\n    \n    inp = tf.keras.layers.Input(shape=(max_len,), dtype=\"int32\")\n    X = transformer(inp)[0]\n    cls_token = X[:,0,:]\n    X = tf.keras.layers.Dropout(0.3)(cls_token)\n    X = tf.keras.layers.Dense(1, activation=\"sigmoid\")(X)\n    model = tf.keras.Model(inputs=inp, outputs=X)\n    return model\n    ","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"train_path = \"../input/jigsaw-multilingual-toxic-comment-classification/jigsaw-toxic-comment-train.csv\"\nval_path = \"../input/jigsaw-multilingual-toxic-comment-classification/validation.csv\"\ntrain = pd.read_csv(train_path, usecols=[\"comment_text\", \"toxic\"])\nval = pd.read_csv(val_path, usecols=[\"comment_text\", \"toxic\"])","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"ids_1, labels_1 = encode_comments(train, tokenizer=bert_tokenizer)\nids_2, labels_2 = encode_comments(train, tokenizer=xlm_tokenizer)\nids_3, labels_3 = encode_comments(train, tokenizer=xlm_roberta_tokenizer)\n\nval_ids_1, val_labels_1 = encode_comments(val, tokenizer=bert_tokenizer)\nval_ids_2, val_labels_2 = encode_comments(val, tokenizer=xlm_tokenizer)\nval_ids_3, val_labels_3 = encode_comments(val, tokenizer=xlm_roberta_tokenizer)\n","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"len(val)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"encode_comments(val, tokenizer=bert_tokenizer)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"AUTO = tf.data.experimental.AUTOTUNE\n\ntpu = tf.distribute.cluster_resolver.TPUClusterResolver()\ntf.config.experimental_connect_to_cluster(tpu)\ntf.tpu.experimental.initialize_tpu_system(tpu)\ntpu_strategy = tf.distribute.experimental.TPUStrategy(tpu)\nprint(tpu_strategy.num_replicas_in_sync)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"batch_size = 16 * tpu_strategy.num_replicas_in_sync\n","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"with tpu_strategy.scope():\n    bert = transformers.TFBertModel.from_pretrained(bert_checkpoint)\n    m1 = make_model(bert)\n    m1.compile(optimizer=tf.keras.optimizers.Adam(3e-5), loss=\"binary_crossentropy\", metrics=[tf.keras.metrics.AUC()])\n    m1.summary()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"h1 = m1.fit(ids_1, labels_1, batch_size=batch_size, validation_data=(val_ids_1, val_labels_1), epochs=1)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"del m1","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"with tpu_strategy.scope():\n    xlm_r = transformers.TFXLMRobertaModel.from_pretrained(\"jplu/tf-xlm-roberta-base\")\n    m3 = make_model(xlm_r)\n    m3.compile(optimizer=tf.keras.optimizers.Adam(3e-5), loss=\"binary_crossentropy\", metrics=[tf.keras.metrics.AUC()])\n    m3.summary()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"with tpu_strategy.scope():\n    xlm = transformers.TFXLMModel.from_pretrained(xlm_checkpoint)\n    m2 = make_model(xlm)\n    m2.compile(optimizer=tf.keras.optimizers.Adam(3e-5), loss=\"binary_crossentropy\", metrics=[tf.keras.metrics.AUC()])\n    m2.summary()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"h3 = m3.fit(ids_3, labels_3, batch_size=batch_size, validation_data=(val_ids_3, val_labels_3), epochs=1)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"del m3","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"h2 = m2.fit(ids_2, labels_2, batch_size=batch_size, validation_data=(val_ids_2, val_labels_2), epochs=1)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"del m2","execution_count":null,"outputs":[]}],"metadata":{"kernelspec":{"language":"python","display_name":"Python 3","name":"python3"},"language_info":{"pygments_lexer":"ipython3","nbconvert_exporter":"python","version":"3.6.4","file_extension":".py","codemirror_mode":{"name":"ipython","version":3},"name":"python","mimetype":"text/x-python"}},"nbformat":4,"nbformat_minor":4}