{"metadata":{"kernelspec":{"language":"python","display_name":"Python 3","name":"python3"},"language_info":{"name":"python","version":"3.7.12","mimetype":"text/x-python","codemirror_mode":{"name":"ipython","version":3},"pygments_lexer":"ipython3","nbconvert_exporter":"python","file_extension":".py"}},"nbformat_minor":4,"nbformat":4,"cells":[{"cell_type":"code","source":"import os\nimport pandas as pd\nimport shutil\n\n# Load the csv file\ndata_df = pd.read_csv('/kaggle/input/prostate-cancer-grade-assessment/train.csv')\n\n# Create a directory for ISUP_0 images\nos.makedirs('/kaggle/working/ISUP_0', exist_ok=True)\n\n# Copy 1000 images for each isup grade to the corresponding directory\nfor grade in range(0, 6):\n    grade_dir = f'/kaggle/working/ISUP_{grade}'\n    os.makedirs(grade_dir, exist_ok=True)\n    counter = 0\n    for index, row in data_df.iterrows():\n        if row['isup_grade'] == grade and counter < 1000:\n            src = '/kaggle/input/tile-pre-processing/' + row['image_id'] + '.png'\n            src = os.path.join(\"/kaggle/input/tile-pre-processing/512x512x3\", os.path.basename(src))\n            dst = grade_dir + '/' + row['image_id'] + '.png'\n            shutil.copy(src, dst)\n            counter += 1\n        if counter == 1000: \n\n            break\n\nprint(\"Number of files in each directory:\")\nfor grade in range(6):\n    grade_dir = f'/kaggle/working/ISUP_{grade}'\n    num_files = len(os.listdir(grade_dir))\n    print(f\"{grade_dir}: {num_files} files\")","metadata":{"_uuid":"8f2839f25d086af736a60e9eeb907d3b93b6e0e5","_cell_guid":"b1076dfc-b9ad-4769-8c92-a6c4dae69d19","trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"import os\nimport pandas as pd\nimport shutil\n\n# Load the csv file\ndata_df = pd.read_csv('/kaggle/input/prostate-cancer-grade-assessment/train.csv')\n\n# Create a directory for ISUP_0 images\nos.makedirs('/kaggle/working/train', exist_ok=True)\n\n# Copy 1000 images for each isup grade to the corresponding directory\nfor grade in range(6):\n    grade_dir = f'/kaggle/working/train/ISUP_{grade}'\n    os.makedirs(grade_dir, exist_ok=True)\n    counter = 0\n    for index, row in data_df.iterrows():\n        if row['isup_grade'] == grade and counter < 1000:\n            src = f'/kaggle/input/prostate-cancer-grade-assessment/train_images/{row[\"image_id\"]}.tiff'\n            dst = f'{grade_dir}/{row[\"image_id\"]}_{row[\"data_provider\"]}.png'\n            shutil.copy(src, dst)\n            counter += 1\n        if counter == 1000: \n            break\n\nprint(\"Number of files in each directory:\")\nfor grade in range(6):\n    grade_dir = f'/kaggle/working/train/ISUP_{grade}'\n    num_files = len(os.listdir(grade_dir))\n    print(f\"{grade_dir}: {num_files} files\")\n","metadata":{"execution":{"iopub.status.busy":"2023-03-21T18:41:12.700154Z","iopub.execute_input":"2023-03-21T18:41:12.701543Z","iopub.status.idle":"2023-03-21T18:46:20.503148Z","shell.execute_reply.started":"2023-03-21T18:41:12.701482Z","shell.execute_reply":"2023-03-21T18:46:20.500867Z"},"trusted":true},"execution_count":1,"outputs":[{"traceback":["\u001b[0;31m---------------------------------------------------------------------------\u001b[0m","\u001b[0;31mKeyboardInterrupt\u001b[0m                         Traceback (most recent call last)","\u001b[0;32m/tmp/ipykernel_27/3516326111.py\u001b[0m in \u001b[0;36m<module>\u001b[0;34m\u001b[0m\n\u001b[1;32m     18\u001b[0m             \u001b[0msrc\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0;34mf'/kaggle/input/prostate-cancer-grade-assessment/train_images/{row[\"image_id\"]}.tiff'\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m     19\u001b[0m             \u001b[0mdst\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0;34mf'{grade_dir}/{row[\"image_id\"]}_{row[\"data_provider\"]}.png'\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m---> 20\u001b[0;31m             \u001b[0mshutil\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mcopy\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0msrc\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mdst\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m     21\u001b[0m             \u001b[0mcounter\u001b[0m \u001b[0;34m+=\u001b[0m \u001b[0;36m1\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m     22\u001b[0m         \u001b[0;32mif\u001b[0m \u001b[0mcounter\u001b[0m \u001b[0;34m==\u001b[0m \u001b[0;36m1000\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n","\u001b[0;32m/opt/conda/lib/python3.7/shutil.py\u001b[0m in \u001b[0;36mcopy\u001b[0;34m(src, dst, follow_symlinks)\u001b[0m\n\u001b[1;32m    246\u001b[0m     \u001b[0;32mif\u001b[0m \u001b[0mos\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mpath\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0misdir\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mdst\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m    247\u001b[0m         \u001b[0mdst\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mos\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mpath\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mjoin\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mdst\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mos\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mpath\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mbasename\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0msrc\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m--> 248\u001b[0;31m     \u001b[0mcopyfile\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0msrc\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mdst\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mfollow_symlinks\u001b[0m\u001b[0;34m=\u001b[0m\u001b[0mfollow_symlinks\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m    249\u001b[0m     \u001b[0mcopymode\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0msrc\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mdst\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mfollow_symlinks\u001b[0m\u001b[0;34m=\u001b[0m\u001b[0mfollow_symlinks\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m    250\u001b[0m     \u001b[0;32mreturn\u001b[0m \u001b[0mdst\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n","\u001b[0;32m/opt/conda/lib/python3.7/shutil.py\u001b[0m in \u001b[0;36mcopyfile\u001b[0;34m(src, dst, follow_symlinks)\u001b[0m\n\u001b[1;32m    120\u001b[0m         \u001b[0;32mwith\u001b[0m \u001b[0mopen\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0msrc\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0;34m'rb'\u001b[0m\u001b[0;34m)\u001b[0m \u001b[0;32mas\u001b[0m \u001b[0mfsrc\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m    121\u001b[0m             \u001b[0;32mwith\u001b[0m \u001b[0mopen\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mdst\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0;34m'wb'\u001b[0m\u001b[0;34m)\u001b[0m \u001b[0;32mas\u001b[0m \u001b[0mfdst\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m--> 122\u001b[0;31m                 \u001b[0mcopyfileobj\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mfsrc\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mfdst\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m    123\u001b[0m     \u001b[0;32mreturn\u001b[0m \u001b[0mdst\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m    124\u001b[0m \u001b[0;34m\u001b[0m\u001b[0m\n","\u001b[0;32m/opt/conda/lib/python3.7/shutil.py\u001b[0m in \u001b[0;36mcopyfileobj\u001b[0;34m(fsrc, fdst, length)\u001b[0m\n\u001b[1;32m     77\u001b[0m     \u001b[0;34m\"\"\"copy data from file-like object fsrc to file-like object fdst\"\"\"\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m     78\u001b[0m     \u001b[0;32mwhile\u001b[0m \u001b[0;36m1\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m---> 79\u001b[0;31m         \u001b[0mbuf\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mfsrc\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mread\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mlength\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m     80\u001b[0m         \u001b[0;32mif\u001b[0m \u001b[0;32mnot\u001b[0m \u001b[0mbuf\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m     81\u001b[0m             \u001b[0;32mbreak\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n","\u001b[0;31mKeyboardInterrupt\u001b[0m: "],"ename":"KeyboardInterrupt","evalue":"","output_type":"error"}]},{"cell_type":"code","source":"import os\nimport shutil\n\ndata_dir = '/kaggle/working'\n\n# list of directories to remove\ndirs_to_remove = ['train']\n\n# iterate over directories and remove them\nfor directory in dirs_to_remove:\n    dir_path = os.path.join(data_dir, directory)\n    if os.path.exists(dir_path):\n        shutil.rmtree(dir_path)","metadata":{"execution":{"iopub.status.busy":"2023-03-21T18:48:57.435255Z","iopub.execute_input":"2023-03-21T18:48:57.435817Z","iopub.status.idle":"2023-03-21T18:48:59.120091Z","shell.execute_reply.started":"2023-03-21T18:48:57.435776Z","shell.execute_reply":"2023-03-21T18:48:59.119082Z"},"trusted":true},"execution_count":2,"outputs":[]},{"cell_type":"code","source":"import os\nimport shutil\nimport random\n\n# set the parent directory\nparent_dir = '/kaggle/working/'\n\n# set the subdirectories\nsubdirs = [\"ISUP_0\", \"ISUP_1\", \"ISUP_2\", \"ISUP_3\", \"ISUP_4\", \"ISUP_5\"]\n\n# set the percentage split for train, val, and test\ntrain_split = 0.6\nval_split = 0.2\ntest_split = 0.2\n\nfor subdir in subdirs:\n    # create directories for train, val, and test data\n    train_dir = os.path.join(parent_dir, \"train\", subdir)\n    os.makedirs(train_dir, exist_ok=True)\n    val_dir = os.path.join(parent_dir, \"val\", subdir)\n    os.makedirs(val_dir, exist_ok=True)\n    test_dir = os.path.join(parent_dir, \"test\", subdir)\n    os.makedirs(test_dir, exist_ok=True)\n    \n    # get all the files in the subdirectory\n    subdir_path = os.path.join(parent_dir, subdir)\n    files = os.listdir(subdir_path)\n    num_files = len(files)\n    \n    # shuffle the files randomly\n    random.shuffle(files)\n    \n    # calculate the number of files for each split\n    num_train = int(num_files * train_split)\n    num_val = int(num_files * val_split)\n    \n    # copy the files to the corresponding directories\n    print(f\"Found {num_files} files in directory {subdir_path}\")\n    print(f\"Copying {num_train} files to train directory\")\n    for i in range(num_train):\n        file = files[i]\n        src = os.path.join(subdir_path, file)\n        dst = os.path.join(train_dir, file)\n        shutil.copy(src, dst)\n    \n    print(f\"Copying {num_val} files to validation directory\")\n    for i in range(num_train, num_train+num_val):\n        file = files[i]\n        src = os.path.join(subdir_path, file)\n        dst = os.path.join(val_dir, file)\n        shutil.copy(src, dst)\n    \n    print(f\"Copying {num_files-num_train-num_val} files to test directory\")\n    for i in range(num_train+num_val, num_files):\n        file = files[i]\n        src = os.path.join(subdir_path, file)\n        dst = os.path.join(test_dir, file)\n        shutil.copy(src, dst)","metadata":{},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Splits your data into training, validation, and test sets and moves the files instead of copying them**","metadata":{}},{"cell_type":"code","source":"import os\nimport shutil\n\ndata_dir = '/kaggle/working'\n\n# list of directories to remove\ndirs_to_remove = ['ISUP_0', 'ISUP_1', 'ISUP_2', 'ISUP_3', 'ISUP_4', 'ISUP_5']\n\n# iterate over directories and remove them\nfor directory in dirs_to_remove:\n    dir_path = os.path.join(data_dir, directory)\n    if os.path.exists(dir_path):\n        shutil.rmtree(dir_path)","metadata":{},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Permanently delete the directories and their contents**","metadata":{}},{"cell_type":"code","source":"import os\nimport numpy as np\nimport tensorflow as tf\nfrom tensorflow import keras\nfrom tensorflow.keras import layers\nfrom PIL import Image\nImage.MAX_IMAGE_PIXELS = 10000000000\n\n# Set the seed for reproducibility\nnp.random.seed(0)\ntf.random.set_seed(0)\n\n# Set the directories\ntrain_dir = \"/kaggle/working/train\"\nval_dir = \"/kaggle/working/val\"\ntest_dir = \"/kaggle/working/test\"\n\n# Set the parameters\nimg_size = (224, 224)\nbatch_size = 32\n\n# Create the train data generator with data augmentation\ntrain_datagen = keras.preprocessing.image.ImageDataGenerator(\n    rescale=1./255,\n    rotation_range=20,\n    width_shift_range=0.2,\n    height_shift_range=0.2,\n    shear_range=0.2,\n    zoom_range=0.2,\n    horizontal_flip=True,\n    fill_mode=\"nearest\",\n)\n\n# Create the validation and test data generators\nval_datagen = keras.preprocessing.image.ImageDataGenerator(rescale=1./255)\ntest_datagen = keras.preprocessing.image.ImageDataGenerator(rescale=1./255)\n\n# Load the train, validation, and test data\ntrain_data = train_datagen.flow_from_directory(\n    train_dir,\n    target_size=img_size,\n    batch_size=batch_size,\n    class_mode=\"categorical\",\n    shuffle=True,\n    seed=0,\n)\n\nval_data = val_datagen.flow_from_directory(\n    val_dir,\n    target_size=img_size,\n    batch_size=batch_size,\n    class_mode=\"categorical\",\n    shuffle=False,\n)\n\ntest_data = test_datagen.flow_from_directory(\n    test_dir,\n    target_size=img_size,\n    batch_size=batch_size,\n    class_mode=\"categorical\",\n    shuffle=False,\n)\n\n# Load the pre-trained model without the top layers\nbase_model = keras.applications.vgg16.VGG16(\n    weights=\"imagenet\",\n    include_top=False,\n    input_shape=(224, 224, 3),\n)\n\n# Freeze the base model layers\nbase_model.trainable = False\n\n# Add new classification layers on top of the pre-trained model\ninputs = keras.Input(shape=(224, 224, 3))\nx = base_model(inputs, training=False)\nx = keras.layers.Flatten()(x)\nx = keras.layers.Dense(512, activation=\"relu\")(x)\nx = keras.layers.Dropout(0.5)(x)\noutputs = keras.layers.Dense(6, activation=\"softmax\")(x)\nmodel = keras.Model(inputs, outputs)\n\n# Compile the model\nmodel.compile(\n    optimizer=keras.optimizers.Adam(learning_rate=0.0001),\n    loss=\"categorical_crossentropy\",\n    metrics=[\"accuracy\"],\n)\n\n# Set early stopping callback\nearly_stopping = keras.callbacks.EarlyStopping(\n    monitor=\"val_loss\",\n    patience=5,\n    verbose=1,\n    mode=\"min\",\n    restore_best_weights=True,\n)\n\n# Set model checkpoint callback\ncheckpoint_callback = keras.callbacks.ModelCheckpoint(\n    filepath='model_checkpoint.h5',\n    monitor='val_loss',\n    verbose=1,\n    save_best_only=True,\n    save_weights_only=False,\n    mode='min',\n    save_freq='epoch'\n)\n\n# Train the model with GPU acceleration and model checkpoint callback\nwith tf.device('/GPU:0'):\n    history = model.fit(\n        train_data,\n        validation_data=val_data,\n        epochs=25,\n        callbacks=[early_stopping, checkpoint_callback],\n    )\n\n# Evaluate the model on the test data\ntest_loss, test_acc = model.evaluate(test_data)\nprint(\"Test loss:\", test_loss)\nprint(\"Test accuracy:\", test_acc)","metadata":{},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**VGG16 Using GPU**","metadata":{}},{"cell_type":"markdown","source":"**A WHOLE NEW APPROACH**","metadata":{}},{"cell_type":"code","source":"import os\nimport cv2\nimport numpy as np\nimport pandas as pd\nfrom sklearn.model_selection import train_test_split\n\n# Load the csv file\ndata_df = pd.read_csv('/kaggle/input/prostate-cancer-grade-assessment/train.csv')\n\n# Define the tile size and stride\ntile_size = 128\nstride = 64\n\n# Create a directory for the tiles\nos.makedirs('/kaggle/working/', exist_ok=True)\n\n# Loop through the images and extract tiles\nfor index, row in data_df.iterrows():\n    img_path = '/kaggle/input/prostate-cancer-grade-assessment/train_images' + row['image_id'] + '.tiff'\n    img = cv2.imread(img_path, cv2.IMREAD_COLOR)\n    height, width, _ = img.shape\n    for y in range(0, height - tile_size + 1, stride):\n        for x in range(0, width - tile_size + 1, stride):\n            tile = img[y:y+tile_size, x:x+tile_size]\n            tile_path = f\"/kaggle/working/{row['image_id']}_x{x}_y{y}.png\"\n            cv2.imwrite(tile_path, tile)\n\n# Split the data into training and validation sets\ntrain_df, val_df = train_test_split(data_df, test_size=0.2, stratify=data_df['isup_grade'], random_state=42)\n\n# Save the training and validation sets to csv files\ntrain_df.to_csv('/path/to/train_tiles.csv', index=False)\nval_df.to_csv('/path/to/val_tiles.csv', index=False)\n","metadata":{"execution":{"iopub.status.busy":"2023-03-21T19:04:43.533977Z","iopub.execute_input":"2023-03-21T19:04:43.534467Z","iopub.status.idle":"2023-03-21T19:04:43.604998Z","shell.execute_reply.started":"2023-03-21T19:04:43.534424Z","shell.execute_reply":"2023-03-21T19:04:43.603104Z"},"trusted":true},"execution_count":4,"outputs":[{"traceback":["\u001b[0;31m---------------------------------------------------------------------------\u001b[0m","\u001b[0;31mAttributeError\u001b[0m                            Traceback (most recent call last)","\u001b[0;32m/tmp/ipykernel_27/1972419581.py\u001b[0m in \u001b[0;36m<module>\u001b[0;34m\u001b[0m\n\u001b[1;32m     19\u001b[0m     \u001b[0mimg_path\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0;34m'/kaggle/input/prostate-cancer-grade-assessment/train_images'\u001b[0m \u001b[0;34m+\u001b[0m \u001b[0mrow\u001b[0m\u001b[0;34m[\u001b[0m\u001b[0;34m'image_id'\u001b[0m\u001b[0;34m]\u001b[0m \u001b[0;34m+\u001b[0m \u001b[0;34m'.tiff'\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m     20\u001b[0m     \u001b[0mimg\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mcv2\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mimread\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mimg_path\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mcv2\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mIMREAD_COLOR\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m---> 21\u001b[0;31m     \u001b[0mheight\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mwidth\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0m_\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mimg\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mshape\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m     22\u001b[0m     \u001b[0;32mfor\u001b[0m \u001b[0my\u001b[0m \u001b[0;32min\u001b[0m \u001b[0mrange\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;36m0\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mheight\u001b[0m \u001b[0;34m-\u001b[0m \u001b[0mtile_size\u001b[0m \u001b[0;34m+\u001b[0m \u001b[0;36m1\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mstride\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m     23\u001b[0m         \u001b[0;32mfor\u001b[0m \u001b[0mx\u001b[0m \u001b[0;32min\u001b[0m \u001b[0mrange\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;36m0\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mwidth\u001b[0m \u001b[0;34m-\u001b[0m \u001b[0mtile_size\u001b[0m \u001b[0;34m+\u001b[0m \u001b[0;36m1\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mstride\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n","\u001b[0;31mAttributeError\u001b[0m: 'NoneType' object has no attribute 'shape'"],"ename":"AttributeError","evalue":"'NoneType' object has no attribute 'shape'","output_type":"error"}]}]}