{"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_minor":4,"nbformat":4,"cells":[{"cell_type":"markdown","source":"# Báo cáo bài tập lớn môn Học máy \n**Giảng viên**: Trần Quốc Long\n\n**Lớp môn học:** INT3405E_20\n\n**Sinh viên:** Kiều Văn Tuyên\n\n**MSSV**: 19021388","metadata":{}},{"cell_type":"markdown","source":"# MÔ TẢ BÀI TOÁN\n* Quora là nền tảng để mọi người có thể học hỏi lẫn nhau bằng cách đặt câu hỏi và trả lời để chia sẻ kiến thức. Mục đích của bài toán này là để phân loại các câu hỏi đặt ra là thuộc loại câu hỏi chân thành hay không chân thành. \n* Những câu hỏi không chân thành thường là những câu đưa ra tuyên bố quan điểm của mình hơn là để tìm những câu trả lời có ích: không trung lập, khiêu khích hoặc chê bai, không có căn cứ thực tế hoặc chứa nội dung khiêu dâm.\n* Input: Câu hỏi dạng text\n* Output: 0/1 (Sincere/ Insincere)","metadata":{}},{"cell_type":"markdown","source":"# PHÂN TÍCH DỮ LIỆU\n","metadata":{}},{"cell_type":"markdown","source":"**Import các thư viện cần thiết:**","metadata":{}},{"cell_type":"code","source":"import numpy as np # linear algebra\nimport pandas as pd # data processing, CSV file I/O (e.g. pd.read_csv)\nimport matplotlib.pyplot as plt \nfrom transformers import AutoTokenizer, AutoModelForSequenceClassification\nfrom fastai.text.all import *\nfrom sklearn.model_selection import train_test_split\nfrom torch.utils.data import Dataset\n\nfrom wordcloud import WordCloud, STOPWORDS\nimport nltk\nfrom nltk.corpus import stopwords\nimport seaborn as sns\n\nfrom nltk.stem import PorterStemmer\nfrom nltk.tokenize import word_tokenize\n\nfrom sklearn.model_selection import train_test_split\nfrom sklearn.feature_extraction.text import CountVectorizer, TfidfVectorizer\nfrom sklearn.linear_model import LogisticRegression\nfrom sklearn.metrics import f1_score, classification_report\nfrom sklearn.pipeline import Pipeline","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:56:59.556269Z","iopub.execute_input":"2022-01-07T12:56:59.556997Z","iopub.status.idle":"2022-01-07T12:56:59.564935Z","shell.execute_reply.started":"2022-01-07T12:56:59.556952Z","shell.execute_reply":"2022-01-07T12:56:59.564026Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**1. Khảo sát dữ liệu**","metadata":{}},{"cell_type":"code","source":"#Import data\npath = \"/kaggle/input/quora-insincere-questions-classification/\"\ntrain_file = pd.read_csv(path + \"train.csv\")\ntest_file = pd.read_csv(path + \"test.csv\")\n\nprint(\"Train_file: \")\ntrain_file.tail()\n","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:56:59.568999Z","iopub.execute_input":"2022-01-07T12:56:59.569632Z","iopub.status.idle":"2022-01-07T12:57:04.716627Z","shell.execute_reply.started":"2022-01-07T12:56:59.569601Z","shell.execute_reply":"2022-01-07T12:57:04.715832Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"print(\"Test_file:\")\ntest_file.head()","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:57:04.719748Z","iopub.execute_input":"2022-01-07T12:57:04.720167Z","iopub.status.idle":"2022-01-07T12:57:04.742001Z","shell.execute_reply.started":"2022-01-07T12:57:04.720129Z","shell.execute_reply":"2022-01-07T12:57:04.740149Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"train_file.shape, test_file.shape","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:57:04.743040Z","iopub.execute_input":"2022-01-07T12:57:04.743279Z","iopub.status.idle":"2022-01-07T12:57:04.757157Z","shell.execute_reply.started":"2022-01-07T12:57:04.743248Z","shell.execute_reply":"2022-01-07T12:57:04.755982Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Nhận xét:**\n\n**File train.csv:**\n* Số dòng: 1306122\n* Số cột: 3 (cột qid, question_text, target)\n\n**File test.csv:**\n* Số dòng: 375806\n* Số cột: 2 (cột qid, question_text)\n\n**Thông tin về các trường:**\n* Cột qid: Đây chính là id của câu hỏi, không có 2 câu hỏi nào có id giống nhau.\n* Cột question_text: Đây chính là cột chứa các câu hỏi. Chúng ta sẽ tiến hành clean dữ liệu trước khi cho vào mô hình để huấn luyện.\n* Cột target: Đây chính là cột chứa kết quả đánh giá câu hỏi có phải chân thành hay không chân thành, câu hỏi question_text có target = 0 sẽ được đánh giá là câu hỏi chân thành, và câu hỏi có target = 1 sẽ được đánh giá là không chân thành.","metadata":{}},{"cell_type":"code","source":"#Ta biểu diễn đồ thị tỉ lệ số câu hỏi chân thành và số câu hỏi không chân thành trong tập train\n\nsincere_ques = train_file[train_file.target == 0]\ninsincere_ques = train_file[train_file.target == 1]\n\nlabel = 'sincere', 'Insincere'\nsize = [(sincere_ques.shape[0] / train_file.shape[0]) * 100, (insincere_ques.shape[0] / train_file.shape[0]) * 100]\nplt.pie(size,labels = label,colors=[\"c\", \"red\"], autopct=\"%.2f%%\")\nplt.axis('equal')\nplt.show()","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:57:04.760617Z","iopub.execute_input":"2022-01-07T12:57:04.761234Z","iopub.status.idle":"2022-01-07T12:57:05.067431Z","shell.execute_reply.started":"2022-01-07T12:57:04.761193Z","shell.execute_reply":"2022-01-07T12:57:05.066782Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"print(\"Tổng số dữ liệu trong tập train: \",train_file.shape[0])\nprint(\"Số câu hỏi chân thành: \", len(train_file[train_file.target == 0]))\nprint(\"Số câu hỏi thiếu chân thành: \",len(train_file[train_file.target == 1]))","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:57:05.071254Z","iopub.execute_input":"2022-01-07T12:57:05.073489Z","iopub.status.idle":"2022-01-07T12:57:05.231571Z","shell.execute_reply.started":"2022-01-07T12:57:05.073452Z","shell.execute_reply":"2022-01-07T12:57:05.230817Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Nhận xét về phân lớp dữ liệu:**\n\nDựa vào biểu đồ trên, ta có thể thấy trong tập train, số lượng câu hỏi đc đánh nhãn là thiếu chân thành chỉ chiếm khoảng 6.19% (80810/1306122 câu) so với tỉ lệ rất cao là 93.81% là những câu hỏi chân thành.\n\nTỉ lệ giữa 2 nhóm câu hỏi này rơi vào khoảng 1:15 => Tập dữ liệu bị mất cân bằng. Điều này sẽ dẫn đến 1 số vấn đề như sau:\n* Đánh giá sai chất lượng mô hình: Với tỉ lệ như trên thì không cần quan tâm đến mô hình ta cũng có thể đạt được độ chính xác cao của metric accuracy, chỉ cần tất cả dự đoán đưa ra đều có target = 0 thì độ chính xác đã đạt gần 94%.\n* Mô hình dự đoán kém chính xác: Vì ở đây, mục tiêu của bài toán là xác định các câu hỏi thiếu chân thành, trong khi sự mất cân bằng trên có thể khiến kết quả dự đoán thường nghiêng về nhóm đa số(target = 0) và kém hiệu quả trên nhóm thiểu số (target = 1).\n\n Do đó không nên lựa chọn độ chính xác(accuracy) làm chỉ số đánh giá mô hình. Thay vào đó ta có thể sử dụng các metric thay thế như: **F1_score, Recall,..**","metadata":{}},{"cell_type":"markdown","source":"**Khảo sát về tần suất các từ xuất hiện trong tập dữ liệu:**\n* **Word clouds**: Hoạt động theo một các đơn giản: Một từ càng xuất hiện nhiều trong văn bản thì từ đó càng lớn và đậm nét hơn trong Word clouds.","metadata":{}},{"cell_type":"code","source":"print('Ảnh word cloud được tạo từ những câu hỏi chân thành:')\nsincere_wordcloud = WordCloud(width=600, height=400, background_color ='black', min_font_size = 10).generate(str(train_file[train_file[\"target\"] == 0][\"question_text\"]))\n#Positive Word cloud\nplt.figure(figsize=(15,6), facecolor=None)\nplt.imshow(sincere_wordcloud)\nplt.axis(\"off\")\nplt.tight_layout(pad=0)\nplt.show();","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:57:05.234993Z","iopub.execute_input":"2022-01-07T12:57:05.235735Z","iopub.status.idle":"2022-01-07T12:57:06.178818Z","shell.execute_reply.started":"2022-01-07T12:57:05.235699Z","shell.execute_reply":"2022-01-07T12:57:06.178143Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"print('Ảnh word cloud được tạo từ những câu hỏi thiếu chân thành:')\ninsincere_wordcloud = WordCloud(width=600, height=400, background_color ='white', min_font_size = 10).generate(str(train_file[train_file[\"target\"] == 1][\"question_text\"]))\n#Positive Word cloud\nplt.figure(figsize=(15,6), facecolor=None)\nplt.imshow(insincere_wordcloud)\nplt.axis(\"off\")\nplt.tight_layout(pad=0)\nplt.show();","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:57:06.179800Z","iopub.execute_input":"2022-01-07T12:57:06.180088Z","iopub.status.idle":"2022-01-07T12:57:06.826249Z","shell.execute_reply.started":"2022-01-07T12:57:06.180057Z","shell.execute_reply":"2022-01-07T12:57:06.824576Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Thống kê những từ phổ biến trong các loại câu hỏi ( loại bỏ các stopwords)**\n\n**Stop Words:** Là những từ thường được sử dụng ( chẳng hạn như 'the', 'an', 'a',..). Để tránh những từ này chiếm dung lượng trong cơ sở dữ liệu hoặc mất thời gian xử lí, chúng ta nên loại bỏ chúng.\n\nThống kê Word clouds ở trên có thể có những stop words, do đó ta cần lọc chúng ra để có một cái nhìn tổng quan hơn\n","metadata":{}},{"cell_type":"code","source":"\n\nstop_words = set(stopwords.words('english'))\nstop_words","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:57:06.827998Z","iopub.execute_input":"2022-01-07T12:57:06.828528Z","iopub.status.idle":"2022-01-07T12:57:06.844369Z","shell.execute_reply.started":"2022-01-07T12:57:06.828482Z","shell.execute_reply":"2022-01-07T12:57:06.843716Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"class Vocabulary(object):\n    # Tham khảo tại:https://www.kaggle.com/kaosmonkey/visualize-sincere-vs-insincere-words\n    def __init__(self):\n        self.vocab = {}\n        self.STOPWORDS = set()\n        self.STOPWORDS = set(stopwords.words('english'))\n    def build_vocab(self, lines):\n        for line in lines: \n            for word in line.split(' '):\n                word = word.lower()\n                if(word in self.STOPWORDS):\n                    continue\n                if(word not in self.vocab):\n                    self.vocab[word] = 0\n                self.vocab[word] += 1\n                ","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:57:06.845670Z","iopub.execute_input":"2022-01-07T12:57:06.845963Z","iopub.status.idle":"2022-01-07T12:57:06.852315Z","shell.execute_reply.started":"2022-01-07T12:57:06.845930Z","shell.execute_reply":"2022-01-07T12:57:06.851524Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"#Vơi các câu hỏi chân thành\nsincere_vocab = Vocabulary()\nsincere_vocab.build_vocab(train_file[train_file['target'] == 0]['question_text'])\nsincere_vocabulary = sorted(sincere_vocab.vocab.items(), reverse=True, key=lambda kv: kv[1])\n# Dùng sns vẽ biểu đồ 10 từ có tần suất xuất hiện cao nhất\nfor word, count in sincere_vocabulary[:10]:\n    print(word, count)\ndf_sincere_vocab = pd.DataFrame(sincere_vocabulary,columns = ['word_sincere', 'frequency'])\nsns.barplot(x = 'word_sincere', y = 'frequency', data = df_sincere_vocab[:10])\n","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:57:06.857119Z","iopub.execute_input":"2022-01-07T12:57:06.857338Z","iopub.status.idle":"2022-01-07T12:57:14.375858Z","shell.execute_reply.started":"2022-01-07T12:57:06.857314Z","shell.execute_reply":"2022-01-07T12:57:14.375184Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"# Tuong tu voi cac cau hoi khong chan thanh\ninsincere_vocab = Vocabulary()\ninsincere_vocab.build_vocab(train_file[train_file['target'] == 1]['question_text'])\ninsincere_vocabulary = sorted(insincere_vocab.vocab.items(), reverse=True, key=lambda kv: kv[1])\nfor word, count in insincere_vocabulary[:10]:\n    print(word, count)\ndf_insincere_vocab = pd.DataFrame(insincere_vocabulary,columns = ['word_insincere', 'frequency'])\nsns.barplot(y = 'word_insincere', x = 'frequency', data = df_insincere_vocab[5:25])\n","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:57:14.377530Z","iopub.execute_input":"2022-01-07T12:57:14.378023Z","iopub.status.idle":"2022-01-07T12:57:15.380464Z","shell.execute_reply.started":"2022-01-07T12:57:14.377987Z","shell.execute_reply":"2022-01-07T12:57:15.379782Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Nhận xét:**\nNhư chúng ta có thể thấy rõ ràng là có  một số từ phản cảm (nội dung khiêu dâm, phân biệt chủng tộc, nhân vật chính trị,..) xuất hiện rất nhiều trong các câu hỏi thiếu chân thành.","metadata":{}},{"cell_type":"markdown","source":"# Text Processing\n\nSau khi đánh giá, ta thấy dữ liệu còn khá phức tạp và nhiễu. Để đơn giản hóa dữ liệu, ta cần tiến hành xử lý dữ  liệu \nbằng một số bước như: Chỉ giữ lại các ký tự chữ và số, loại bỏ các stop word, đưa các từ về đúng dạng gốc,...\n\n**Tokenization :** (tách từ) là một trong những bước quan trọng nhất trong quá trình tiền xử lý văn bản. Nói một cách đơn giản,\ntokenization là quá trình tách một cụm từ, câu, đoạn văn, một hoặc nhiều tài liệu văn bản thành các đơn vị nhỏ hơn. Mỗi đơn vị \nnhỏ hơn này được gọi là Tokens.\n\n**Stemming vs. lemmatization:** Với mục đích là giảm các dạng vô hướng của mỗi từ thành một cơ sở hoặc gốc chung.\n\nStemming là kĩ thuật dùng để biến đổi 1 từ về dạng gốc( được gọi là stem hoặc root form) bằng cách cực kỳ đơn giản là loại bỏ 1 số\nký tự nằm ở cuối từ mà nó nghĩ rằng là biến thể của từ. \nVí dụ như chúng ta thấy các từ như walked, walking, walks chỉ khác nhau là ở\nnhững ký tự cuối cùng, bằng cách bỏ đi các hậu tố -ed, -ing hoặc -s, chúng ta sẽ được từ nguyên gốc là walk. Tuy nhiên stemming \nkhông thể đưa được các động từ bất quy tắc về dạng gốc được.\n\nKhác với Stemming là xử lý bằng cách loại bỏ các ký tự cuối từ một cách rất heuristic, Lemmatization sẽ xử lý thông minh hơn bằng một bộ\ntừ điển hoặc một bộ ontology nào đó. \nĐiều này sẽ đảm bảo rằng các từ như “goes“, “went” và “go” sẽ chắc chắn có kết quả trả về là như nhau.\nKể các từ danh từ như mouse, mice cũng đều được đưa về cùng một dạng như nhau. \n\n\n\n","metadata":{}},{"cell_type":"code","source":"train_file = train_file[['question_text', 'target']]\n# def text_processing(data_file):\n#     stemmer = PorterStemmer()\n#     #Thực hiện processing:\n#     data_file['txt_processed'] = data_file['question_text'].apply(lambda train_file: word_tokenize(train_file))\n#     print('step1 done...')\n#     data_file['txt_processed'] = data_file['txt_processed'].apply(lambda x: [item for item in x if item.isalpha()])\n#     print('step2 done..')\n#     data_file['txt_processed'] = data_file['txt_processed'].apply(lambda x: [item for item in x if item not in stop_words])\n#     print('step3 done..')\n#     data_file['txt_processed'] = data_file['txt_processed'].apply(lambda x: [stemmer.stem(item) for item in x])\n#     print('done')\n#     return data_file","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:57:15.381694Z","iopub.execute_input":"2022-01-07T12:57:15.382032Z","iopub.status.idle":"2022-01-07T12:57:15.415909Z","shell.execute_reply.started":"2022-01-07T12:57:15.381994Z","shell.execute_reply":"2022-01-07T12:57:15.415207Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"# train_file_sw = text_processing(train_file)\n# train_file_sw.tail()","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:57:15.417092Z","iopub.execute_input":"2022-01-07T12:57:15.417908Z","iopub.status.idle":"2022-01-07T12:57:15.421487Z","shell.execute_reply.started":"2022-01-07T12:57:15.417855Z","shell.execute_reply":"2022-01-07T12:57:15.420332Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"# Không tách stop word\ndef text_processing_nosw(data_file):\n    stemmer = PorterStemmer()\n    #Thực hiện processing:\n    data_file['txt_processed'] = data_file['question_text'].apply(lambda train_file: word_tokenize(train_file))\n    print('step1 done...')\n    data_file['txt_processed'] = data_file['txt_processed'].apply(lambda x: [item for item in x if item.isalpha()])\n    print('step2 done..')\n    data_file['txt_processed'] = data_file['txt_processed'].apply(lambda x: [stemmer.stem(item) for item in x])\n    print('done')\n    return data_file","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:57:15.422966Z","iopub.execute_input":"2022-01-07T12:57:15.423720Z","iopub.status.idle":"2022-01-07T12:57:15.432326Z","shell.execute_reply.started":"2022-01-07T12:57:15.423684Z","shell.execute_reply":"2022-01-07T12:57:15.431643Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"train_file_nw = text_processing_nosw(train_file)\ntrain_file_nw.tail()","metadata":{"execution":{"iopub.status.busy":"2022-01-07T12:57:15.433761Z","iopub.execute_input":"2022-01-07T12:57:15.434227Z","iopub.status.idle":"2022-01-07T13:07:03.722645Z","shell.execute_reply.started":"2022-01-07T12:57:15.434190Z","shell.execute_reply":"2022-01-07T13:07:03.721949Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Nhận xét:** \n* \nKhông tách stop words giúp kết quả f1_scored cao hơn dù không nhiều, đối với CountVectorizer + Logistic Regression kết quả f1_score tăng từ 0.62 (đã chạy ở version 5) lên 0.64","metadata":{}},{"cell_type":"markdown","source":"# Huấn luyện Model","metadata":{}},{"cell_type":"markdown","source":"**Metric: F-score**\n\nMetric phù hợp nhất trong bài này sẽ là f1-scored\n\n**Precision và Recall**\n* Precision của lớp A:Là số lượng mẫu đoán đúng là A / số lượng mẫu đoán là A\n\\begin{align*}p &=\\frac{TP}{TP + FP}\\\\\\\\ &=\\frac{\\sum_{i=1}^n \\mathbb I(y_i = h(x_i) = A)}{\\sum_{i=1}^n \\mathbb I(h(x_i) = A)}\\end{align*}\n\n* Recall của lớp A: Là số lượng mẫu đoán đúng là A / số lượng mẫu là A:\n\\begin{align*}r &= \\frac{TP}{TP + FN}\\\\\\\\&= \\frac{\\sum_{i =1}^n \\mathbb{I}(y_i = h(x_i) = A)}{\\sum_{i = 1}^n \\mathbb{I}(y_i = A)}\\end{align*}\n\nTuy nhiên, chỉ có Precision hay chỉ có Recall thì không đánh giá được chất lượng mô hình.\n* Chỉ dùng Precision, mô hình chỉ đưa ra dự đoán cho một điểm mà nó chắc chắn nhất. Khi đó Precision = 1, tuy nhiên ta không thể nói là mô hình này tốt.\n* Chỉ dùng Recall, nếu mô hình dự đoán tất cả các điểm đều là positive. Khi đó Recall = 1, tuy nhiên ta cũng không thể nói đây là mô hình tốt\n\nKhi đó F1-score được sử dụng. F1-score là trung bình điều hòa (harmonic mean) của precision và recall (giả sử hai đại lượng này khác 0). F1-score được tinh theo công thức:\n\n  ![](https://obrunet.github.io/images/2019-09-16-Quora/f1.png)\n\n\n\n","metadata":{}},{"cell_type":"code","source":"# Hàm tính fscore của model\ndef get_fscore_matrix(fitted_clf, model_name):\n    print(model_name, ' :')\n    \n    # get classes predictions for the classification report \n    y_train_pred, y_pred = fitted_clf.predict(X_train), fitted_clf.predict(X_test)\n    print(classification_report(y_test, y_pred), '\\n') # target_names=y\n    \n    # computes probabilities keep the ones for the positive outcome only      \n    print(f'F1-score = {f1_score(y_test, y_pred):.2f}')","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:07:03.724037Z","iopub.execute_input":"2022-01-07T13:07:03.724299Z","iopub.status.idle":"2022-01-07T13:07:03.731309Z","shell.execute_reply.started":"2022-01-07T13:07:03.724264Z","shell.execute_reply":"2022-01-07T13:07:03.730593Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Model sử dụng: Logicstic Regression**\n* Trong thư viện **Sklearn** cũng có hỗ trợ mô hình Logicstics, nên ta sẽ dùng vào bài toán.\n* Về Logicstic Regression, có thể xem tham khảo tại: https://tricky-tax-444.notion.site/02-H-i-quy-Logistics-cf099245442c461aa36305456a17183e","metadata":{}},{"cell_type":"markdown","source":"**Cách tiếp cận đầu tiên: TF-IDF (Term Frequency - Inverse Document Frequency)**\n* **TF-IDF (Term Frequency – Inverse Document Frequency)** là 1 kĩ thuật sử dụng trong khai phá dữ liệu văn bản, giúp đánh trọng số cho mỗi từ trong văn bản, trong đó TF là tần số xuất hiện của từ trong văn bản và idf là tần số nghịch giúp làm giảm giá trị của những từ phổ biến.Trọng số này được sử dụng để đánh giá tầm quan trọng của một từ trong một văn bản. Giá trị cao thể hiện độ quan trọng cao và nó phụ thuộc vào số lần từ xuất hiện trong văn bản nhưng bù lại bởi tần suất của từ đó trong tập dữ liệu.\n\n* **TF: Term Frequency(Tần suất xuất hiện của từ)**: là số lần từ xuất hiện trong văn bản.Vì các văn bản có thể có độ dài ngắn khác nhau nên một số từ có thể xuất hiện nhiều lần trong một văn bản dài hơn là một văn bản ngắn. Như vậy, term frequency thường được chia cho độ dài văn bản( tổng số từ trong một văn bản).\n\n* **IDF: Inverse Document Frequency(Nghịch đảo tần suất của văn bản)** : giúp đánh giá tầm quan trọng của một từ. Khi tính toán TF , tất cả các từ được coi như có độ quan trọng bằng nhau. Nhưng một số từ như “a”, “the” và “that” thường xuất hiện rất nhiều lần nhưng độ quan trọng là không cao. Như thế chúng ta cần giảm độ quan trọng của những từ này xuốn\n\n* Khi đó, những từ có giá trị tf-idf cao là những từ xuất hiện nhiều trong câu này, và xuất hiện ít trong  câu khác. Việc này giúp ta lọc ra được những từ phổ biến và giữ lại những từ có giá trị cao ( từ khóa của câu đó )\n\n","metadata":{}},{"cell_type":"code","source":"\n\nvectorizer = TfidfVectorizer(lowercase=False, analyzer=lambda x: x, min_df=0.01, max_df=0.999)\ntf_idf = vectorizer.fit_transform(train_file_nw['txt_processed']).toarray()\n\ntf_idf = vectorizer.fit_transform(train_file_nw['txt_processed']).toarray()\n# Split the data (Bộ dữ liệu train_file sẽ được chia ra như sau: 80% tập dữ liệu sẽ được dùng để huấn luyện, và 20% còn lại sẽ được dùng để test.)\nX_train, X_test, y_train, y_test = train_test_split(tf_idf, train_file_nw['target'], test_size=0.2, random_state=42)\n\n\n#Use logictics\nmodel = LogisticRegression(class_weight={0:y_train.sum(), 1:len(y_train) - y_train.sum()}, C=30, max_iter=200, n_jobs=-1)\nmodel.fit(X_train, y_train)\nget_fscore_matrix(model, 'LogisticRegression')","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:07:03.732651Z","iopub.execute_input":"2022-01-07T13:07:03.732936Z","iopub.status.idle":"2022-01-07T13:10:38.573582Z","shell.execute_reply.started":"2022-01-07T13:07:03.732903Z","shell.execute_reply":"2022-01-07T13:10:38.572625Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"Như có thể thấy ở trên, nếu chỉ dùng TF-IDF kết hợp với Logicstic Regression, kết quả cho ra khá thấp, chỉ là 0.3","metadata":{}},{"cell_type":"markdown","source":"**Cách tiếp cận khác: a CountVectorizer / Logistic Regression**\n\nĐể sử dụng dữ liệu văn bản cho mô hình dự đoán, văn bản phải được phân tích cú pháp để loại bỏ một số từ nhất định - quá trình này được gọi là mã hóa. Sau đó, những từ này cần được mã hóa dưới dạng số nguyên hoặc giá trị dấu phẩy động, để sử dụng làm đầu vào trong các thuật toán học máy. Quá trình này được gọi là feature extraction (hay vectorization).\n\n**CountVectorizer** được sử dụng để chuyển đổi một tập hợp các tài liệu văn bản thành một vectơ có số lượng từ khóa / mã thông báo. Nó cũng cho phép xử lý trước dữ liệu văn bản trước khi tạo biểu diễn vectơ. Chức năng này làm cho nó trở thành một mô-đun biểu diễn tính năng rất linh hoạt cho văn bản. Ví dụ minh họa như hình dưới đấy\n\n![image.png](attachment:4b42b817-a5e2-414b-a5f5-e3fe98bb3406.png)","metadata":{},"attachments":{"4b42b817-a5e2-414b-a5f5-e3fe98bb3406.png":{"image/png":"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"}}},{"cell_type":"markdown","source":"Đầu tiên, để thực hiện ta cần nối các từ đã tách ở txt_processed thành một chuỗi","metadata":{}},{"cell_type":"code","source":"# Convert a collection of text documents to string\ntrain_file_nw['str_processed'] = train_file_nw['txt_processed'].apply(lambda x: \" \".join(x))\ntrain_file_nw.head()","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:10:38.575382Z","iopub.execute_input":"2022-01-07T13:10:38.575663Z","iopub.status.idle":"2022-01-07T13:10:39.725950Z","shell.execute_reply.started":"2022-01-07T13:10:38.575624Z","shell.execute_reply":"2022-01-07T13:10:39.725103Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Sử dụng Pipeline**","metadata":{}},{"cell_type":"code","source":"\npipeline = Pipeline([(\"cv\", CountVectorizer(analyzer=\"word\", ngram_range=(1,4), max_df=0.9)),\n                     (\"clf\", LogisticRegression(solver=\"saga\", class_weight=\"balanced\", C=0.5, max_iter=250, verbose=1, n_jobs=-1))])","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:10:39.727087Z","iopub.execute_input":"2022-01-07T13:10:39.727341Z","iopub.status.idle":"2022-01-07T13:10:39.732761Z","shell.execute_reply.started":"2022-01-07T13:10:39.727307Z","shell.execute_reply":"2022-01-07T13:10:39.731745Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"X_train, X_test, y_train, y_test = train_test_split(train_file_nw['str_processed'], train_file_nw.target, test_size=0.2, stratify = train_file_nw.target.values)","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:10:39.734048Z","iopub.execute_input":"2022-01-07T13:10:39.734545Z","iopub.status.idle":"2022-01-07T13:10:40.666087Z","shell.execute_reply.started":"2022-01-07T13:10:39.734509Z","shell.execute_reply":"2022-01-07T13:10:40.665337Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"pl_model = pipeline.fit(X_train, y_train)\npl_model","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:10:40.667525Z","iopub.execute_input":"2022-01-07T13:10:40.667778Z","iopub.status.idle":"2022-01-07T13:25:05.535495Z","shell.execute_reply.started":"2022-01-07T13:10:40.667745Z","shell.execute_reply":"2022-01-07T13:25:05.534724Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"get_fscore_matrix(pl_model, 'Pipeline:')","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:25:05.539545Z","iopub.execute_input":"2022-01-07T13:25:05.541629Z","iopub.status.idle":"2022-01-07T13:26:24.381341Z","shell.execute_reply.started":"2022-01-07T13:25:05.541591Z","shell.execute_reply":"2022-01-07T13:26:24.379814Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Kết luận:**\n* Đầu tiên ta sử dụng TF-IDF, nhưng chúng ta có thể thấy là nó thực sự không hiệu quả.\n* Thay vào đó, sử dụng CountVectorizer với Logistic Regression là hiệu quả hơn rất nhiều \n","metadata":{}},{"cell_type":"markdown","source":"**Submission**","metadata":{}},{"cell_type":"code","source":"pd.read_csv(\"../input/quora-insincere-questions-classification/sample_submission.csv\").head()","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:26:24.382799Z","iopub.execute_input":"2022-01-07T13:26:24.383072Z","iopub.status.idle":"2022-01-07T13:26:24.765550Z","shell.execute_reply.started":"2022-01-07T13:26:24.383038Z","shell.execute_reply":"2022-01-07T13:26:24.764821Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"test_file = text_processing_nosw(test_file)\ntest_file['str_processed'] = test_file['txt_processed'].apply(lambda x: \" \".join(x))\ntest_file.head()\n\n","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:26:24.766718Z","iopub.execute_input":"2022-01-07T13:26:24.767058Z","iopub.status.idle":"2022-01-07T13:29:14.837598Z","shell.execute_reply.started":"2022-01-07T13:26:24.767020Z","shell.execute_reply":"2022-01-07T13:29:14.836800Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"y_pred_final = pl_model.predict(test_file['str_processed'])\ndf_submission = pd.DataFrame({\"qid\":test_file[\"qid\"], \"prediction\":y_pred_final})\ndf_submission.head()","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:29:14.840437Z","iopub.execute_input":"2022-01-07T13:29:14.840668Z","iopub.status.idle":"2022-01-07T13:29:36.482299Z","shell.execute_reply.started":"2022-01-07T13:29:14.840642Z","shell.execute_reply":"2022-01-07T13:29:36.481626Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"df_submission.to_csv('submission.csv', index=False)","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:29:36.483621Z","iopub.execute_input":"2022-01-07T13:29:36.484061Z","iopub.status.idle":"2022-01-07T13:29:37.259147Z","shell.execute_reply.started":"2022-01-07T13:29:36.484025Z","shell.execute_reply":"2022-01-07T13:29:37.258393Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"# Training model sử dụng pretrained BERT\n\nNhư đã có ở kết quả ở trên, điểm f1_score là 0.64, cũng khá ổn. Tuy nhiên, ta sẽ thử cải thiện kết quả này bằng cách sử dụng BERT - một mô hình rất mạnh\n\n**Giới thiệu về BERT**\n\nCuối năm 2018, các nhà nghiên cứu làm việc tại Google AI giới thiệu một một kiến trúc mới cho lớp bài toán Language Representation: BERT - viết tắt của Bidirectional Encoder Representations from Transformers. Đây là mô hình được huấn luyện trước từ các văn bản không được gán nhãn.\n\nĐiểm khác biệt lớn nhất so với các mô hình đã có trước đó là mô hình BERT mới này được thiết kế để biểu diễn ngôn ngữ bằng cách xem xét ngữ cảnh 2 chiều cả bên trái và bên phải.  Sau đó, vector biểu diễn ngôn ngữ có thể được tinh chỉnh (bằng một lớp đầu ra bổ sung), ứng dụng cho một loạt các nhiệm vụ, đặc biệt không yêu cầu sửa đổi quá nhiều kiến trúc để phục vụ cho bài toán mới. Điều này góp phần cải thiện hiệu quả khi sử dụng biểu diễn ngôn ngữ được huấn luyện trước cho các tác vụ về sau theo hướng tiếp cận fine-tuning.\n\nSau đây, ta sẽ áp dụng BERT vào bài toán đã cho.","metadata":{}},{"cell_type":"code","source":"tokenizer = AutoTokenizer.from_pretrained('bert-base-cased')","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:29:37.260277Z","iopub.execute_input":"2022-01-07T13:29:37.262540Z","iopub.status.idle":"2022-01-07T13:29:48.353285Z","shell.execute_reply.started":"2022-01-07T13:29:37.262498Z","shell.execute_reply":"2022-01-07T13:29:48.352611Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"class QuoraDataset(Dataset):\n    def __init__(self, X, y, tokenizer):\n        self.text = X.reset_index(drop=True)\n        self.targets = y.reset_index(drop=True)\n        self.tok = tokenizer\n    def __len__(self):\n        return len(self.text)\n    \n    def __getitem__(self, idx):\n        \n        text = self.text[idx]\n        targ = self.targets[idx]\n        \n        return self.tok(text, padding='max_length', \n                        truncation=True,\n                        max_length=30,\n                        return_tensors=\"pt\")[\"input_ids\"][0], tensor(targ)","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:29:48.357010Z","iopub.execute_input":"2022-01-07T13:29:48.357210Z","iopub.status.idle":"2022-01-07T13:29:48.363808Z","shell.execute_reply.started":"2022-01-07T13:29:48.357186Z","shell.execute_reply":"2022-01-07T13:29:48.362746Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"# Split data\nX_train, X_valid, y_train, y_valid = train_test_split(train_file[\"question_text\"], train_file[\"target\"], \n                                                      stratify=train_file[\"target\"],  test_size=0.1)","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:29:48.365286Z","iopub.execute_input":"2022-01-07T13:29:48.365730Z","iopub.status.idle":"2022-01-07T13:29:49.795885Z","shell.execute_reply.started":"2022-01-07T13:29:48.365691Z","shell.execute_reply":"2022-01-07T13:29:49.795116Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"train_ds = QuoraDataset(X_train, y_train, tokenizer) # train dataset\nvalid_ds = QuoraDataset(X_valid, y_valid, tokenizer) # valid dataset","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:29:49.797245Z","iopub.execute_input":"2022-01-07T13:29:49.797506Z","iopub.status.idle":"2022-01-07T13:29:49.945940Z","shell.execute_reply.started":"2022-01-07T13:29:49.797473Z","shell.execute_reply":"2022-01-07T13:29:49.945182Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"# Prepare data loader\ntrain_dl = DataLoader(train_ds, bs=128)\nvalid_dl = DataLoader(valid_ds, bs=256)\ndata_loader = DataLoaders(train_dl, valid_dl).to(\"cuda\")","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:29:49.947197Z","iopub.execute_input":"2022-01-07T13:29:49.947452Z","iopub.status.idle":"2022-01-07T13:29:49.954528Z","shell.execute_reply.started":"2022-01-07T13:29:49.947420Z","shell.execute_reply":"2022-01-07T13:29:49.952080Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"# Sử dụng BERT model\n\nbert = AutoModelForSequenceClassification.from_pretrained('bert-base-cased').train()\nclassifier = nn.Sequential(\n    nn.Linear(768, 1024),\n    nn.ReLU(),\n    nn.Dropout(0.5),\n    nn.Linear(1024, 2)\n)\nbert.classifier = classifier\nclass BertClassifier(Module):\n    def __init__(self, bert):\n        self.bert = bert\n    def forward(self, x):\n        x = self.bert(x)\n        return x.logits\n\nmodel = BertClassifier(bert).to(\"cuda\")","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:29:49.957065Z","iopub.execute_input":"2022-01-07T13:29:49.957393Z","iopub.status.idle":"2022-01-07T13:30:39.665103Z","shell.execute_reply.started":"2022-01-07T13:29:49.957361Z","shell.execute_reply":"2022-01-07T13:30:39.664338Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"\nnum_sin = (train_file[\"target\"] == 0).sum() # số câu hỏi chân thành\nnum_insin = (train_file[\"target\"] == 1).sum() # Số câu hỏi không chân thành\nn = num_sin + num_insin\nclass_weights = tensor([n / (n+num_sin), n / (n+num_insin)]).to('cuda')\nlearn = Learner(data_loader, model, \n                loss_func=nn.CrossEntropyLoss(weight=class_weights), \n                metrics=[accuracy, F1Score()]).to_fp16()\nlearn.lr_find() # Biểu thị bảng learning rate\n","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:30:39.666448Z","iopub.execute_input":"2022-01-07T13:30:39.666742Z","iopub.status.idle":"2022-01-07T13:31:11.983505Z","shell.execute_reply.started":"2022-01-07T13:30:39.666707Z","shell.execute_reply":"2022-01-07T13:31:11.982747Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"Ở đây,ta sẽ sử dụng lr.find() để tìm learning rate cho hợp lý. Như đã thấy ở biểu đồ trên thì ở khoảng 0.001 và 0.01  là khá tốt, có giá trị loss thấp. Do đó ta sẽ chọn learning rate = 2e^-5 ( xấp xỉ = 0.01) để train mô hình.","metadata":{}},{"cell_type":"code","source":"learn.fit_one_cycle(2, lr_max=2e-5)","metadata":{"execution":{"iopub.status.busy":"2022-01-07T13:31:11.984742Z","iopub.execute_input":"2022-01-07T13:31:11.985015Z","iopub.status.idle":"2022-01-07T15:48:29.889410Z","shell.execute_reply.started":"2022-01-07T13:31:11.984980Z","shell.execute_reply":"2022-01-07T15:48:29.888745Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Nhận xét:** \n* Dùng model BERT đem lại kết quả f1_scored cao hơn so với việc sử dụng CountVectorizer + Logistic Regression\n* Đặc biệt là ta không cần phải xử lí dữ liệu trước khi tiến hành train, vì BERT đã thay ta làm điều đó r.\n* Tuy nhiên, trong cuộc thi này ta không được phép sử dụng các dữ liệu bên ngoài. Vì thế việc chạy thử BERT chỉ mang tính chất nhận xét về sức mạnh của nó.","metadata":{}},{"cell_type":"markdown","source":"# Báo cáo kết quả\n1. Đối với CountVectorizer và Logistic Regression: Kết quả khi submit đạt cao nhất là 0.63691 đối với Private score và đạt 0.63 đối với public score\n\n![image.png](attachment:510f5ee3-a18c-4bc0-81fe-27c2dbd17e2d.png)\n\n2. Sử dụng Bert model: điểm F1_score đạt cao nhất là 0.719. ( ở version 22 )","metadata":{},"attachments":{"510f5ee3-a18c-4bc0-81fe-27c2dbd17e2d.png":{"image/png":"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"}}}]}