{"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":"# **Importar libreria**","metadata":{}},{"cell_type":"code","source":"import os\nimport torch\nimport torch.nn as nn\nimport pandas as pd\nimport numpy as np\nimport matplotlib.pyplot as plt\nimport matplotlib\nimport pydicom as dicom\nimport cv2\nimport ast\n\nimport glob\nimport re\nimport math\nfrom tqdm.notebook import tqdm\nimport seaborn as sns\nimport warnings\nwarnings.filterwarnings(\"ignore\")\nfrom pydicom.pixel_data_handlers.util import apply_voi_lut\nimport tensorflow as tf\nfrom tensorflow import keras\nfrom tensorflow.keras.callbacks import ModelCheckpoint, EarlyStopping, ReduceLROnPlateau\nfrom keras import applications ","metadata":{"_uuid":"8f2839f25d086af736a60e9eeb907d3b93b6e0e5","_cell_guid":"b1076dfc-b9ad-4769-8c92-a6c4dae69d19","execution":{"iopub.status.busy":"2022-06-17T19:03:07.716020Z","iopub.execute_input":"2022-06-17T19:03:07.717089Z","iopub.status.idle":"2022-06-17T19:03:14.450513Z","shell.execute_reply.started":"2022-06-17T19:03:07.716338Z","shell.execute_reply":"2022-06-17T19:03:14.449734Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"#Enlace de la base de datos\npath = '/kaggle/input/rsna-miccai-brain-tumor-radiogenomic-classification/'\nos.listdir(path)","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:14.452430Z","iopub.execute_input":"2022-06-17T19:03:14.453077Z","iopub.status.idle":"2022-06-17T19:03:14.462454Z","shell.execute_reply.started":"2022-06-17T19:03:14.453038Z","shell.execute_reply":"2022-06-17T19:03:14.461205Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"# **Cargar base de datos**","metadata":{}},{"cell_type":"code","source":"train_data = pd.read_csv(path+'train_labels.csv')\nsamp_subm  = pd.read_csv(path+'sample_submission.csv')\n\nprint(train_data.head(7)),print(samp_subm.head())","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:14.463606Z","iopub.execute_input":"2022-06-17T19:03:14.464009Z","iopub.status.idle":"2022-06-17T19:03:14.506032Z","shell.execute_reply.started":"2022-06-17T19:03:14.463968Z","shell.execute_reply":"2022-06-17T19:03:14.505005Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"# **2 Compresión de los datos** \nMetodologia Crisp-DM","metadata":{}},{"cell_type":"code","source":"#Imprimir tamaño de carpetas por TRAIN Y TEST\nprint('Samples train:', len(train_data))\nprint('Samples test:', len(samp_subm))","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:14.507828Z","iopub.execute_input":"2022-06-17T19:03:14.508539Z","iopub.status.idle":"2022-06-17T19:03:14.514192Z","shell.execute_reply.started":"2022-06-17T19:03:14.508502Z","shell.execute_reply":"2022-06-17T19:03:14.513123Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"train_data.head(7)","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:14.517386Z","iopub.execute_input":"2022-06-17T19:03:14.518161Z","iopub.status.idle":"2022-06-17T19:03:14.529844Z","shell.execute_reply.started":"2022-06-17T19:03:14.518113Z","shell.execute_reply":"2022-06-17T19:03:14.528620Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"## analisis de datos faltantes\nprint(pd.isnull(train_data).sum()) \nprint('___________')\nprint(pd.isnull(samp_subm ).sum())","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:14.531765Z","iopub.execute_input":"2022-06-17T19:03:14.532183Z","iopub.status.idle":"2022-06-17T19:03:14.541753Z","shell.execute_reply.started":"2022-06-17T19:03:14.532143Z","shell.execute_reply":"2022-06-17T19:03:14.540834Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"train_data[\"MGMT_value\"].value_counts()","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:14.543178Z","iopub.execute_input":"2022-06-17T19:03:14.543677Z","iopub.status.idle":"2022-06-17T19:03:14.555373Z","shell.execute_reply.started":"2022-06-17T19:03:14.543641Z","shell.execute_reply":"2022-06-17T19:03:14.554529Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"to_exclude = [109, 123, 709]\n\ntrain_data = train_data[~train_data['BraTS21ID'].isin(to_exclude)]\nnum_samples = train_data.shape[0]\nnum_positives = np.sum(train_data['MGMT_value'] == 1)\nnum_negatives = np.sum(train_data['MGMT_value'] == 0)\n\n\ntrain_data[\"MGMT_value\"].value_counts().head(2).plot(kind = 'pie',autopct='%1.1f%%', figsize=(8, 8)).legend()\n\n\ntrain_data.hist(column=\"MGMT_value\")","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:14.557448Z","iopub.execute_input":"2022-06-17T19:03:14.558301Z","iopub.status.idle":"2022-06-17T19:03:15.119161Z","shell.execute_reply.started":"2022-06-17T19:03:14.558265Z","shell.execute_reply":"2022-06-17T19:03:15.118443Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"samp_subm.head()","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:15.122936Z","iopub.execute_input":"2022-06-17T19:03:15.124922Z","iopub.status.idle":"2022-06-17T19:03:15.138957Z","shell.execute_reply.started":"2022-06-17T19:03:15.124883Z","shell.execute_reply":"2022-06-17T19:03:15.137928Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"#analizar una carpeta 100--->00150\nfolder = str(train_data.loc[100, 'BraTS21ID']).zfill(5)\nfolder","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:15.143863Z","iopub.execute_input":"2022-06-17T19:03:15.144221Z","iopub.status.idle":"2022-06-17T19:03:15.158028Z","shell.execute_reply.started":"2022-06-17T19:03:15.144185Z","shell.execute_reply":"2022-06-17T19:03:15.157279Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"## CONTENIDO DE LAS CARPETAS\nos.listdir(path+'train/'+folder)","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:15.162250Z","iopub.execute_input":"2022-06-17T19:03:15.164543Z","iopub.status.idle":"2022-06-17T19:03:15.182308Z","shell.execute_reply.started":"2022-06-17T19:03:15.164502Z","shell.execute_reply":"2022-06-17T19:03:15.181660Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"Explicacion de las tecnicas T2w, T1wCE, T1w, FLAIR\n![](https://i.postimg.cc/3NS5z6RB/image.png)\n","metadata":{}},{"cell_type":"code","source":"#numero de imagenes por capeta\nprint('Number of FLAIR images:', len(os.listdir(path+'train/'+folder+'/'+'FLAIR')))\nprint('Number of T1w images:',   len(os.listdir(path+'train/'+folder+'/'+'T1w')))\nprint('Number of T1wCE images:', len(os.listdir(path+'train/'+folder+'/'+'T1wCE')))\nprint('Number of T2w images:',   len(os.listdir(path+'train/'+folder+'/'+'T2w')))","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:15.183463Z","iopub.execute_input":"2022-06-17T19:03:15.183976Z","iopub.status.idle":"2022-06-17T19:03:15.233624Z","shell.execute_reply.started":"2022-06-17T19:03:15.183940Z","shell.execute_reply":"2022-06-17T19:03:15.232986Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"#Cargar imagenes\npath_file = ''.join([path, 'train/', folder, '/', 'FLAIR/'])\nimage = os.listdir(path_file)[0]\ndata_file = dicom.dcmread(path_file+image)\nimg = data_file.pixel_array","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:15.234405Z","iopub.execute_input":"2022-06-17T19:03:15.234703Z","iopub.status.idle":"2022-06-17T19:03:15.254497Z","shell.execute_reply.started":"2022-06-17T19:03:15.234674Z","shell.execute_reply":"2022-06-17T19:03:15.253326Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"#Forma de la imagen (Tamaño)\nprint('Image shape:', img.shape)\n###print(train_data.shape)","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:15.260365Z","iopub.execute_input":"2022-06-17T19:03:15.260706Z","iopub.status.idle":"2022-06-17T19:03:15.264554Z","shell.execute_reply.started":"2022-06-17T19:03:15.260670Z","shell.execute_reply":"2022-06-17T19:03:15.263734Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"## IMAGENES FLAIR\ndef plot_examples(row = 0, cat = 'FLAIR'): \n    folder = str(train_data.loc[row, 'BraTS21ID']).zfill(5)\n    path_file = ''.join([path, 'train/', folder, '/', cat, '/'])\n    images = os.listdir(path_file)\n    \n    fig, axs = plt.subplots(1, 5, figsize=(30, 30))\n    fig.subplots_adjust(hspace = .2, wspace=.2)\n    axs = axs.ravel()\n    \n    for num in range(5):\n        data_file = dicom.dcmread(path_file+images[num])\n        img = data_file.pixel_array\n        axs[num].imshow(img, cmap='gray')\n        axs[num].set_title(cat+' '+images[num])\n        axs[num].set_xticklabels([])\n        axs[num].set_yticklabels([])\n        \nrow = 0\nplot_examples(row = row, cat = 'FLAIR')","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:15.265709Z","iopub.execute_input":"2022-06-17T19:03:15.266603Z","iopub.status.idle":"2022-06-17T19:03:16.343835Z","shell.execute_reply.started":"2022-06-17T19:03:15.266563Z","shell.execute_reply":"2022-06-17T19:03:16.343065Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"##IMAGENES T1W\nplot_examples(row = row, cat = 'T1w')","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:16.344837Z","iopub.execute_input":"2022-06-17T19:03:16.345195Z","iopub.status.idle":"2022-06-17T19:03:17.136172Z","shell.execute_reply.started":"2022-06-17T19:03:16.345160Z","shell.execute_reply":"2022-06-17T19:03:17.134714Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"## IMAGENES T1CE\nplot_examples(row = row, cat = 'T1wCE')","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:17.137406Z","iopub.execute_input":"2022-06-17T19:03:17.138084Z","iopub.status.idle":"2022-06-17T19:03:17.994013Z","shell.execute_reply.started":"2022-06-17T19:03:17.138044Z","shell.execute_reply":"2022-06-17T19:03:17.992493Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"##IMAGENES T2W\nplot_examples(row = row, cat = 'T2w')","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:17.995253Z","iopub.execute_input":"2022-06-17T19:03:17.996085Z","iopub.status.idle":"2022-06-17T19:03:18.771506Z","shell.execute_reply.started":"2022-06-17T19:03:17.996045Z","shell.execute_reply":"2022-06-17T19:03:18.770746Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"![](https://i.pinimg.com/originals/15/7f/99/157f9957ecd64da6b079ff5189dbf3ff.gif)","metadata":{}},{"cell_type":"markdown","source":"# **3 Preparacion de los datos**\n\nPREPROCESAMIENTO DE IMAGEN\n\nPara cada paciente, realizaremos un preprocesado de las imágenes aplicando estas diferentes modificaciones:\n* Cargue una secuencia ordenada de 64 resonancias magnéticas\n* Recortar imágenes para reducir los bordes negros\n* Cambiar el tamaño de la imagen para reducir los 0 de la matriz para el modelo previo al entrenamiento\n* Aplicar filtro de eliminación de ruido\n* Convierta cada imagen en una matriz 3D\n","metadata":{}},{"cell_type":"code","source":"#Datos\ndata_directory = '../input/rsna-miccai-brain-tumor-radiogenomic-classification/'\ntrain_df = pd.read_csv(data_directory+\"train_labels.csv\")\ntrain_df['BraTS21ID5'] = [format(x, '05d') for x in train_df.BraTS21ID]\ntrain_df.head(3)\ntest = pd.read_csv(\n    data_directory+'sample_submission.csv')\n\ntest['BraTS21ID5'] = [format(x, '05d') for x in test.BraTS21ID]","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:18.772690Z","iopub.execute_input":"2022-06-17T19:03:18.773159Z","iopub.status.idle":"2022-06-17T19:03:18.786606Z","shell.execute_reply.started":"2022-06-17T19:03:18.773122Z","shell.execute_reply":"2022-06-17T19:03:18.785885Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"IMAGE_SIZE = 240\nSCALE = .8\nNUM_IMAGES = 64\nMRI_TYPE = \"FLAIR\"","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:18.787884Z","iopub.execute_input":"2022-06-17T19:03:18.788230Z","iopub.status.idle":"2022-06-17T19:03:18.792498Z","shell.execute_reply.started":"2022-06-17T19:03:18.788193Z","shell.execute_reply":"2022-06-17T19:03:18.791635Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"#CARGAR IMAEGN dicom, RECORTAR Y APLICAR FILTRO DENOISING \ndef load_dicom_image(\n    path,\n    img_size=IMAGE_SIZE,\n    scale=SCALE):\n# Cargar imagen \n    img = dicom.read_file(path).pixel_array\n    # recorte imagen\n    center_x, center_y = img.shape[1] / 2, img.shape[0] / 2\n    width_scaled, height_scaled = img.shape[1] * scale, img.shape[0] * scale\n    left_x, right_x = center_x - width_scaled / 2, center_x + width_scaled / 2\n    top_y, bottom_y = center_y - height_scaled / 2, center_y + height_scaled / 2\n    img = img[int(top_y):int(bottom_y), int(left_x):int(right_x)]\n\n    img = cv2.resize(img, (img_size, img_size))\n    #cv2.fastNlMeansDenoisingMulti() \n    \n    # Convertir en matriz 3D\n    img = np.repeat(img[..., np.newaxis], 3, -1)\n    \n    return img","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:18.793768Z","iopub.execute_input":"2022-06-17T19:03:18.794569Z","iopub.status.idle":"2022-06-17T19:03:18.804321Z","shell.execute_reply.started":"2022-06-17T19:03:18.794531Z","shell.execute_reply":"2022-06-17T19:03:18.803419Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"![](http://people.tuebingen.mpg.de/burger/neural_denoising/images/denoising.png)","metadata":{}},{"cell_type":"markdown","source":"Podemos verificar el resultado de estos diferentes pasos de preprocesamiento","metadata":{}},{"cell_type":"code","source":"sample_img = dicom.read_file(\n    data_directory+\"train/00046/FLAIR/Image-115.dcm\").pixel_array\npreproc_img = load_dicom_image(data_directory+\"train/00046/FLAIR/Image-115.dcm\")\n\n\nfig = plt.figure(figsize=(12,8))\nax1 = plt.subplot(1,2,1)\nax1.imshow(sample_img, cmap=\"gray\")\nax1.set_title(f\"Original image shape = {sample_img.shape}\")\nax2 = plt.subplot(1,2,2)\nax2.imshow(preproc_img[:,:,0], cmap=\"gray\")\nax2.set_title(f\"Preproc image shape = {preproc_img.shape}\")\nplt.show()","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:18.805540Z","iopub.execute_input":"2022-06-17T19:03:18.806805Z","iopub.status.idle":"2022-06-17T19:03:19.152292Z","shell.execute_reply.started":"2022-06-17T19:03:18.806672Z","shell.execute_reply":"2022-06-17T19:03:19.151588Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"Selecionamos imagen central de cada carpeta y selecionamos igual numero de imaganes a cada lado (Evitar imagenes negras)","metadata":{}},{"cell_type":"code","source":"def load_dicom_images_3d(\n    scan_id, \n    num_imgs=NUM_IMAGES, \n    img_size=IMAGE_SIZE, \n    mri_type=MRI_TYPE, \n    split=\"train\"):\n    \n    files = sorted(glob.glob(f\"{data_directory}{split}/{scan_id}/{mri_type}/*.dcm\"), \n               key=lambda var:[int(x) if x.isdigit() else x for x in re.findall(r'[^0-9]|[0-9]+', var)])\n\n    middle = len(files)//2\n    num_imgs2 = num_imgs//2\n    p1 = max(0, middle - num_imgs2)\n    p2 = min(len(files), middle + num_imgs2)\n    img3d = np.stack([load_dicom_image(f) for f in files[p1:p2]]) \n    if img3d.shape[0] < num_imgs:\n        n_zero = np.zeros((num_imgs - img3d.shape[0], img_size, img_size, 3))\n        img3d = np.concatenate((img3d,  n_zero), axis = 0)\n            \n    return img3d","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:19.153453Z","iopub.execute_input":"2022-06-17T19:03:19.154274Z","iopub.status.idle":"2022-06-17T19:03:19.162713Z","shell.execute_reply.started":"2022-06-17T19:03:19.154235Z","shell.execute_reply":"2022-06-17T19:03:19.162050Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"Prueba de carga de una secuencia de imágenes preprocesadas para un paciente:","metadata":{}},{"cell_type":"code","source":"sample_seq = load_dicom_images_3d(\"00046\")\nprint(\"Shape of the sequence is:\", sample_seq.shape)\nprint(\"Dimension of the 15th image in sequence is:\", sample_seq[15].shape)\nfig = plt.figure(figsize=(5,5))\nplt.imshow(np.squeeze(sample_seq[15][:,:,0]), cmap=\"gray\")\nplt.show()","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:19.165399Z","iopub.execute_input":"2022-06-17T19:03:19.165804Z","iopub.status.idle":"2022-06-17T19:03:20.112695Z","shell.execute_reply.started":"2022-06-17T19:03:19.165753Z","shell.execute_reply":"2022-06-17T19:03:20.111975Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"# **4 Modelado**","metadata":{}},{"cell_type":"markdown","source":"CARGAR MODELO RESNET50 PREENTRENADO\nPara realizar el Transfer Learning sobre cada imagen de la secuencia, cargaremos un modelo preentrenado gracias a Keras.applications con los pesos preentrenados en ImageNet.\n\n![](https://i0.wp.com/www.datasmarts.net/wp-content/uploads/2019/10/1_IlzW43-NtJrwqtt5Xy3ISA.jpeg?fit=750%2C300&ssl=1)","metadata":{}},{"cell_type":"code","source":"base_resnet = keras.applications.ResNet50(\n    weights=None,\n    #weights=\"imagenet\",\n    pooling='avg',\n    input_shape=(IMAGE_SIZE, IMAGE_SIZE, 3),\n    include_top=False)\n\n\"\"\"\nbase_resnet.save_weights(\n'base_resnet_imagenet.h5')\n\n\"\"\"\n#base_resnet.load_weights(\n# '../input/resnet-imagenet-weights/base_resnet_imagenet.h5')\n","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:20.113832Z","iopub.execute_input":"2022-06-17T19:03:20.115040Z","iopub.status.idle":"2022-06-17T19:03:25.755060Z","shell.execute_reply.started":"2022-06-17T19:03:20.115002Z","shell.execute_reply":"2022-06-17T19:03:25.753293Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"También vamos a corregir todas las capas del modelo para que no se vuelvan a entrenar para la detección de características. La capa de clasificación tampoco se carga (include_top = False).","metadata":{}},{"cell_type":"code","source":"base_resnet.trainable = False","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:25.756657Z","iopub.execute_input":"2022-06-17T19:03:25.757291Z","iopub.status.idle":"2022-06-17T19:03:25.774619Z","shell.execute_reply.started":"2022-06-17T19:03:25.757214Z","shell.execute_reply":"2022-06-17T19:03:25.773810Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"* Crear una matriz en base a RESNET50 para cada secuencia de paciente\n* modelo ResNet50 para obtener los pesos segun la predicción de cada imagen de los pacientes.\n* Creamos una matriz global que agrupará las secuencias de x matrices ResNet50 para todos los pacientes.","metadata":{}},{"cell_type":"code","source":"train = train_df[['BraTS21ID5','MGMT_value']]\nX_train = train['BraTS21ID5'].values\ny_train = train['MGMT_value'].values","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:25.776053Z","iopub.execute_input":"2022-06-17T19:03:25.776695Z","iopub.status.idle":"2022-06-17T19:03:25.784852Z","shell.execute_reply.started":"2022-06-17T19:03:25.776654Z","shell.execute_reply":"2022-06-17T19:03:25.783771Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"listMatrix = []\nfor i, patient in enumerate(tqdm(X_train)):\n    listVectors = []\n    sequence = load_dicom_images_3d(scan_id=str(patient),mri_type=MRI_TYPE)\n    for j in range(len(sequence)):\n        img = sequence[j]\n        img = np.expand_dims(img, axis=0)\n        img = tf.keras.applications.resnet50.preprocess_input(img)\n        img_vector = base_resnet.predict(img)\n        listVectors.append(np.array(img_vector))\n    \n    PatientMatrix = np.stack(listVectors)\n    listMatrix.append(PatientMatrix)","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:03:25.787061Z","iopub.execute_input":"2022-06-17T19:03:25.787898Z","iopub.status.idle":"2022-06-17T19:36:14.998940Z","shell.execute_reply.started":"2022-06-17T19:03:25.787854Z","shell.execute_reply":"2022-06-17T19:36:14.997997Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"Veamos ahora las formas de las matrices obtenidas tras la aplicación de este Learning Transfer:","metadata":{}},{"cell_type":"code","source":"print(f\"Number of patient matrix: {len(listMatrix)}\")\nprint(f\"Patient matrix shape: {listMatrix[0].shape}\")","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:36:15.000571Z","iopub.execute_input":"2022-06-17T19:36:15.004076Z","iopub.status.idle":"2022-06-17T19:36:15.010506Z","shell.execute_reply.started":"2022-06-17T19:36:15.004034Z","shell.execute_reply":"2022-06-17T19:36:15.009532Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"![](https://aprendeconalf.es/docencia/python/manual/img/arrays.png)","metadata":{}},{"cell_type":"code","source":"#np.array(listMatrix, dtype=object).shape","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:36:15.013148Z","iopub.execute_input":"2022-06-17T19:36:15.016084Z","iopub.status.idle":"2022-06-17T19:36:15.023750Z","shell.execute_reply.started":"2022-06-17T19:36:15.016040Z","shell.execute_reply":"2022-06-17T19:36:15.022673Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"aplicar LSTM para la clasificacion\nLas redes neuronales recurrentes (RNN) son ampliamente utilizadas en inteligencia artificial cuando una noción temporal está involucrada en los datos.\n","metadata":{}},{"cell_type":"code","source":"model_input_dim = listMatrix[0].shape[2]","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:36:15.025365Z","iopub.execute_input":"2022-06-17T19:36:15.026255Z","iopub.status.idle":"2022-06-17T19:36:15.039139Z","shell.execute_reply.started":"2022-06-17T19:36:15.026199Z","shell.execute_reply":"2022-06-17T19:36:15.038111Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"def get_sequence_model():\n    '''Definicion de la arquitectura LSTM '''\n    model = keras.models.Sequential()\n    model.add(keras.layers.LSTM(100, input_shape=(NUM_IMAGES, model_input_dim), return_sequences=True))\n    model.add(keras.layers.Dropout(0.2))\n    model.add(keras.layers.Dense(100, activation='relu'))\n    model.add(keras.layers.Dense(1, activation='sigmoid'))\n    return model","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:45:11.455993Z","iopub.execute_input":"2022-06-17T19:45:11.456448Z","iopub.status.idle":"2022-06-17T19:45:11.462586Z","shell.execute_reply.started":"2022-06-17T19:45:11.456412Z","shell.execute_reply":"2022-06-17T19:45:11.461529Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"![](https://upload.wikimedia.org/wikipedia/commons/f/f2/K-fold_cross_validation.jpg)\n\n# Explicacion K-FOLD  ↓","metadata":{}},{"cell_type":"code","source":"from sklearn.model_selection import KFold\n\ninputs = np.array(listMatrix)\ntargets = np.array(y_train).astype('float32').reshape((-1,1))\n\nnum_folds = 5\n\n# Definir la validación cruzada de K-fold\nkfold = KFold(n_splits=num_folds, shuffle=True)\n\n# Evaluación del modelo K-fold Cross Validation\nhistory = {}\nfold_no = 1\nfor train_df, valid_df in kfold.split(inputs, targets):\n    \n    train_dataset = tf.data.Dataset.from_tensor_slices((inputs[train_df], targets[train_df]))\n    valid_dataset = tf.data.Dataset.from_tensor_slices((inputs[valid_df], targets[valid_df]))\n    \n    model = get_sequence_model()\n    model.compile(loss='binary_crossentropy', \n                  optimizer='adam', \n                  metrics='accuracy')\n    \n    # Define callbacks.\n    model_save = ModelCheckpoint(f'Brain_lstm_kfold_{fold_no}.h5', \n                                 save_best_only = True, \n                                 monitor = 'val_accuracy', \n                                 mode = 'max', verbose = 1)\n    early_stop = EarlyStopping(monitor = 'val_accuracy', \n                               patience = 25, mode = 'max', verbose = 1,\n                               restore_best_weights = True)\n    \n    print('------------------------------------------------------------------------')\n    print(f'Training for fold {fold_no} ...')\n    \n    epochs = 200\n    history[fold_no] = model.fit(\n        train_dataset,\n        validation_data=valid_dataset, \n        epochs=epochs, \n        batch_size=32,\n        callbacks = [model_save, early_stop])\n    \n    # Aumentar el número de pliegues\n    fold_no += 1","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:45:16.662658Z","iopub.execute_input":"2022-06-17T19:45:16.663328Z","iopub.status.idle":"2022-06-17T19:50:36.112637Z","shell.execute_reply.started":"2022-06-17T19:45:16.663289Z","shell.execute_reply":"2022-06-17T19:50:36.111427Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"Ahora entrenaremos este modelo LSTM en las matrices compiladas para cada paciente utilizando Transfer Learning ResNet50.\n\nSe configura un EarlyStopping y se guardará el mejor modelo.\n\nAhora veamos los resultados de este entrenamiento:","metadata":{}},{"cell_type":"code","source":"fig, ax = plt.subplots(1, 2, figsize=(20, 7))\nax = ax.ravel()\n\nfor fold in history:\n    for i, metric in enumerate([\"accuracy\",\"loss\"]):\n        ax[i].plot(history[fold].history[metric], label=\"train \"+str(fold))\n        ax[i].plot(history[fold].history[\"val_\" + metric], linestyle=\"dotted\", label=\"val \"+str(fold))\n        ax[i].set_title(\"Model {}\".format(metric))\n        ax[i].set_xlabel(\"epochs\")\n        ax[i].set_ylabel(metric)\n        ax[i].legend()","metadata":{"execution":{"iopub.status.busy":"2022-06-17T19:51:52.485016Z","iopub.execute_input":"2022-06-17T19:51:52.485887Z","iopub.status.idle":"2022-06-17T19:51:52.940433Z","shell.execute_reply.started":"2022-06-17T19:51:52.485845Z","shell.execute_reply":"2022-06-17T19:51:52.936966Z"},"trusted":true},"execution_count":null,"outputs":[]}]}