{"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":"code","source":"import pandas as pd\nfrom sklearn.preprocessing import MultiLabelBinarizer\nimport matplotlib.pyplot as plt\nimport tensorflow as tf\nimport numpy as np","metadata":{"_uuid":"8f2839f25d086af736a60e9eeb907d3b93b6e0e5","_cell_guid":"b1076dfc-b9ad-4769-8c92-a6c4dae69d19","trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"#load data\ndf = pd.read_csv('../input/plant-pathology-2021-fgvc8/train.csv', index_col='image')\n#nhãn bằng chữ ban đầu của từng mẫu\nlabels = df.labels.values.copy()\ndf","metadata":{"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Chuẩn hóa dữ liệu**","metadata":{}},{"cell_type":"code","source":"label_unique = df.labels.unique()\nprint(label_unique)","metadata":{"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"#format train data\ntrain_Y = df['labels'].values.copy() \n# nhìn vào dữ liệu ta thấy rằng 1 mẫu dữ liệu có thể có nhiều nhãn, vậy đây là bài toán đa nhãn\ndf['labels'] = [x.split(' ') for x in df['labels']] \nclasses = ['complex', 'frog_eye_leaf_spot', 'powdery_mildew', 'rust', 'scab', 'healthy']\nscores = MultiLabelBinarizer(classes=classes).fit_transform(df['labels'].values)\ndf = pd.DataFrame(columns=classes, data=scores, index=df.index)\n# df.to_csv('train.csv')\ndf.head()","metadata":{"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"df.value_counts()","metadata":{"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Ta nhận thấy rằng tuy đây là bài toán đa nhãn nhưng nhìn vào thực tế những mẫu đã được gán nhãn heathy rồi thì sẽ không gán được những nhãn khác, vậy ta sẽ xây dựng 5 model cho 5 nhãn:complex, frog_eye_leaf_spot, powdery_mildew, rust, scab. Mẫu dữ liệu không được gán nhãn nào trong 5 nhãn trên sẽ đc gán là healthy**","metadata":{}},{"cell_type":"code","source":"x = [df[x].sum() for x in classes]\ny = classes\ny","metadata":{"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"plt.style.use('bmh')\nplt.xticks(fontsize =12)\nplt.yticks(fontsize =12)\nplt.xlabel('Category',fontsize =13)\nplt.ylabel('Quantity of Image',fontsize = 13)\nplt.xticks(rotation=50)\ncolor_list = ['#f8a709', '#FF6565', '#2CC9FB', '#37DE5B', '#FF74E9', '#2C99FE']\nplt.bar(y,x, color = color_list,width=0.6)\n\nplt.show()\nprint(\"Số mẫu dữ liệu: \", len(df))","metadata":{"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Nhìn vào biểu đồ trên, ta thấy rằng có một số lớp khá ít dữ liệu, nên khi chia dữ liệu dễ bị miss nên ta dùng 5-fold cross validation**","metadata":{}},{"cell_type":"markdown","source":"**> Chia fold","metadata":{}},{"cell_type":"code","source":"from sklearn.model_selection import KFold\nkfold = KFold(n_splits=5, shuffle=True, random_state = 42)\nfold_ids = np.zeros(len(df))\nfor i, (train_ids, val_ids) in enumerate(kfold.split(df.index, labels)):\n    fold_ids[val_ids] = i\n\nvalue_counts = lambda x: pd.Series.value_counts(x, normalize=True)\ndf_five_folds = pd.DataFrame({\n    'origin_data': df.apply(value_counts).loc[1],\n    'fold_0': df[fold_ids == 0].apply(value_counts).loc[1],\n    'fold_1': df[fold_ids == 1].apply(value_counts).loc[1],\n    'fold_2': df[fold_ids == 2].apply(value_counts).loc[1],\n    'fold_3': df[fold_ids == 3].apply(value_counts).loc[1],\n    'fold_4': df[fold_ids == 4].apply(value_counts).loc[1]})\n\nbar = df_five_folds.plot.bar(figsize=[10, 10], colormap='Spectral', rot=50)\n\nfolds = pd.DataFrame({\n    'image': df.index,\n    'fold': fold_ids})\n\nfolds.to_csv('folds.csv', index=False)","metadata":{"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"> Khi sử dụng KFold ta thấy phân bố nhãn trong các fold so với phân bố nhãn trong dữ liệu train ban đầu bị lệch nhau. Với StratifiedKFold ta sẽ thu được tỉ lệ này cân bằng hơn khá nhiều. Với phương pháp này thì nó sẽ chỉ shuffle dữ liệu một lần đầu tiên trước khi bắt đầu chia fold và nó sẽ cố gắng chia sao cho tỷ lệ các class trong các fold là tương đồng nhau.","metadata":{}},{"cell_type":"code","source":"from sklearn.model_selection import StratifiedKFold\nkfold = StratifiedKFold(n_splits=5, shuffle=True, random_state = 42)\nfold_ids = np.zeros(len(df))\nfor i, (train_ids, val_ids) in enumerate(kfold.split(df.index, labels)):\n    fold_ids[val_ids] = i\n\nvalue_counts = lambda x: pd.Series.value_counts(x, normalize=True)\ndf_five_folds = pd.DataFrame({\n    'origin_data': df.apply(value_counts).loc[1],\n    'fold_0': df[fold_ids == 0].apply(value_counts).loc[1],\n    'fold_1': df[fold_ids == 1].apply(value_counts).loc[1],\n    'fold_2': df[fold_ids == 2].apply(value_counts).loc[1],\n    'fold_3': df[fold_ids == 3].apply(value_counts).loc[1],\n    'fold_4': df[fold_ids == 4].apply(value_counts).loc[1]})\n\nbar = df_five_folds.plot.bar(figsize=[10, 10], colormap='Spectral', rot=50)\n\nfolds = pd.DataFrame({\n    'image': df.index,\n    'fold': fold_ids})\n\nfolds.to_csv('folds.csv', index=False)","metadata":{"trusted":true},"execution_count":null,"outputs":[]}]}