{"metadata":{"kernelspec":{"language":"python","display_name":"Python 3","name":"python3"},"language_info":{"name":"python","version":"3.11.13","mimetype":"text/x-python","codemirror_mode":{"name":"ipython","version":3},"pygments_lexer":"ipython3","nbconvert_exporter":"python","file_extension":".py"},"kaggle":{"accelerator":"none","dataSources":[{"sourceId":3362,"databundleVersionId":31148,"sourceType":"competition"}],"dockerImageVersionId":31089,"isInternetEnabled":true,"language":"python","sourceType":"notebook","isGpuEnabled":false}},"nbformat_minor":4,"nbformat":4,"cells":[{"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)\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 20GB 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","metadata":{"_uuid":"8f2839f25d086af736a60e9eeb907d3b93b6e0e5","_cell_guid":"b1076dfc-b9ad-4769-8c92-a6c4dae69d19","trusted":true,"execution":{"iopub.status.busy":"2025-07-27T11:51:53.001317Z","iopub.execute_input":"2025-07-27T11:51:53.001652Z","iopub.status.idle":"2025-07-27T11:51:55.721508Z","shell.execute_reply.started":"2025-07-27T11:51:53.001619Z","shell.execute_reply":"2025-07-27T11:51:55.720452Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"# 使用する外部ライブラリーのインポート\nimport zipfile\nimport os\nimport tensorflow as tf\nimport numpy as np\nimport matplotlib.pyplot as plt\nfrom PIL import Image\nimport glob\nfrom sklearn.model_selection import train_test_split\nimport shutil\nfrom tensorflow.keras import layers, models\nfrom tensorflow.keras.applications import EfficientNetB3\nfrom tensorflow.keras.callbacks import EarlyStopping\nimport random","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T11:52:37.966158Z","iopub.execute_input":"2025-07-27T11:52:37.966484Z","iopub.status.idle":"2025-07-27T11:52:57.757034Z","shell.execute_reply.started":"2025-07-27T11:52:37.966457Z","shell.execute_reply":"2025-07-27T11:52:57.756129Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"with zipfile.ZipFile('/kaggle/input/dogs-vs-cats-redux-kernels-edition/train.zip', 'r') as zip_ref:\n    zip_ref.extractall('/kaggle/working/')\n\n\nwith zipfile.ZipFile('/kaggle/input/dogs-vs-cats-redux-kernels-edition/test.zip', 'r') as zip_ref:\n    zip_ref.extractall('/kaggle/working/')","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T12:07:47.853344Z","iopub.execute_input":"2025-07-27T12:07:47.853648Z","iopub.status.idle":"2025-07-27T12:07:47.876338Z","shell.execute_reply.started":"2025-07-27T12:07:47.853628Z","shell.execute_reply":"2025-07-27T12:07:47.874995Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"import os\nprint(os.listdir('/kaggle/input'))\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T12:08:30.321232Z","iopub.execute_input":"2025-07-27T12:08:30.321563Z","iopub.status.idle":"2025-07-27T12:08:30.32728Z","shell.execute_reply.started":"2025-07-27T12:08:30.32154Z","shell.execute_reply":"2025-07-27T12:08:30.326295Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"import os\nprint(os.listdir('/kaggle/input/dogs-vs-cats'))\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T12:09:03.509498Z","iopub.execute_input":"2025-07-27T12:09:03.509815Z","iopub.status.idle":"2025-07-27T12:09:03.515104Z","shell.execute_reply.started":"2025-07-27T12:09:03.509792Z","shell.execute_reply":"2025-07-27T12:09:03.514204Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"import zipfile\n\n# 正しいパスに修正\nwith zipfile.ZipFile('/kaggle/input/dogs-vs-cats/train.zip', 'r') as zip_ref:\n    zip_ref.extractall('/kaggle/working/')\n\nwith zipfile.ZipFile('/kaggle/input/dogs-vs-cats/test1.zip', 'r') as zip_ref:\n    zip_ref.extractall('/kaggle/working/')\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T12:09:30.619517Z","iopub.execute_input":"2025-07-27T12:09:30.619843Z","iopub.status.idle":"2025-07-27T12:09:42.623322Z","shell.execute_reply.started":"2025-07-27T12:09:30.619821Z","shell.execute_reply":"2025-07-27T12:09:42.622192Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"import os\n\ntrain_dir = '/kaggle/working/train'\ntest_dir = '/kaggle/working/test1'\n\nprint(\"Train images:\", len(os.listdir(train_dir)))\nprint(\"Test images:\", len(os.listdir(test_dir)))\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T12:09:57.784175Z","iopub.execute_input":"2025-07-27T12:09:57.785755Z","iopub.status.idle":"2025-07-27T12:09:57.837324Z","shell.execute_reply.started":"2025-07-27T12:09:57.785698Z","shell.execute_reply":"2025-07-27T12:09:57.836005Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"# 解凍済みの画像フォルダ\nimg_dir = '/kaggle/working/train'\n\n# 画像ファイル名一覧（JPEGのみ）\nall_images = [f for f in os.listdir(img_dir) if f.endswith('.jpg')]\n\n# 猫と犬のファイルを分ける\ncat_images = [f for f in all_images if f.startswith('cat')]\ndog_images = [f for f in all_images if f.startswith('dog')]\n\n# 猫・犬からそれぞれランダムに3枚ずつ\nsample_cats = random.sample(cat_images, 3)\nsample_dogs = random.sample(dog_images, 3)\n\n# 画像表示（3枚 × 2行）\nplt.figure(figsize=(12, 6))\n\n# 猫画像（1行目）\nfor i, fname in enumerate(sample_cats):\n    img_path = os.path.join(img_dir, fname)\n    img = Image.open(img_path)\n    plt.subplot(2, 3, i + 1)\n    plt.imshow(img)\n    plt.title(f\"Cat: {fname}\")\n    plt.axis('off')\n\n# 犬画像（2行目）\nfor i, fname in enumerate(sample_dogs):\n    img_path = os.path.join(img_dir, fname)\n    img = Image.open(img_path)\n    plt.subplot(2, 3, i + 4)\n    plt.imshow(img)\n    plt.title(f\"Dog: {fname}\")\n    plt.axis('off')\n\nplt.tight_layout()\nplt.show()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T12:10:46.170213Z","iopub.execute_input":"2025-07-27T12:10:46.170951Z","iopub.status.idle":"2025-07-27T12:10:47.049464Z","shell.execute_reply.started":"2025-07-27T12:10:46.17089Z","shell.execute_reply":"2025-07-27T12:10:47.048412Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"IMG_SIZE = 128  # EfficientNetB3に合わせる\nBATCH_SIZE = 32","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T12:11:06.598014Z","iopub.execute_input":"2025-07-27T12:11:06.598356Z","iopub.status.idle":"2025-07-27T12:11:06.603217Z","shell.execute_reply.started":"2025-07-27T12:11:06.59833Z","shell.execute_reply":"2025-07-27T12:11:06.602129Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"# ファイルパスとラベルのペアを作成\nall_files = [(os.path.join(img_dir, fname), 0 if fname.startswith('cat') else 1) for fname in all_images]\nrandom.shuffle(all_files)\n\n# train/valid分割\ntrain_files, val_files = train_test_split(all_files, test_size=0.2, random_state=42)\n\n# 画像読み込みと加工\ndef process_image(path, label):\n    img = tf.io.read_file(path)\n    img = tf.image.decode_jpeg(img, channels=3)\n    img = tf.image.resize(img, [IMG_SIZE, IMG_SIZE])\n    img = img / 255.0\n    return img, label\n\n# Dataset生成関数\ndef create_dataset(file_label_list):\n    paths, labels = zip(*file_label_list)\n    ds = tf.data.Dataset.from_tensor_slices((list(paths), list(labels)))\n    ds = ds.map(process_image).batch(BATCH_SIZE).prefetch(tf.data.AUTOTUNE)\n    return ds\n\ntrain_ds = create_dataset(train_files)\nval_ds = create_dataset(val_files)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T12:11:44.922783Z","iopub.execute_input":"2025-07-27T12:11:44.923136Z","iopub.status.idle":"2025-07-27T12:11:45.636484Z","shell.execute_reply.started":"2025-07-27T12:11:44.923109Z","shell.execute_reply":"2025-07-27T12:11:45.635443Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"model = models.Sequential([\n    layers.Conv2D(32, (3, 3), activation='relu', input_shape=(IMG_SIZE, IMG_SIZE, 3)),\n    layers.MaxPooling2D(2, 2),\n    \n    layers.Conv2D(64, (3, 3), activation='relu'),\n    layers.MaxPooling2D(2, 2),\n    \n    layers.Conv2D(128, (3, 3), activation='relu'),\n    layers.MaxPooling2D(2, 2),\n    \n    layers.Flatten(),\n    layers.Dense(128, activation='relu'),\n    layers.Dropout(0.3),\n    layers.Dense(1, activation='sigmoid')  # 2クラス分類\n])\n\n\nmodel.compile(optimizer='adam',\n              loss='binary_crossentropy',\n              metrics=['accuracy'])\n\nmodel.summary()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T12:12:00.622287Z","iopub.execute_input":"2025-07-27T12:12:00.622588Z","iopub.status.idle":"2025-07-27T12:12:00.815699Z","shell.execute_reply.started":"2025-07-27T12:12:00.622568Z","shell.execute_reply":"2025-07-27T12:12:00.814007Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"early_stop = EarlyStopping(patience=3, restore_best_weights=True)\n\nhistory = model.fit(\n    train_ds,\n    validation_data=val_ds,\n    epochs=10,\n    callbacks=[early_stop]\n)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T14:17:53.635013Z","iopub.execute_input":"2025-07-27T14:17:53.63534Z","iopub.status.idle":"2025-07-27T14:43:28.843962Z","shell.execute_reply.started":"2025-07-27T14:17:53.635317Z","shell.execute_reply":"2025-07-27T14:43:28.842895Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"loss, acc = model.evaluate(val_ds)\nprint(f\"✅ 検証データでの精度: {acc:.4f}\")","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T14:53:41.640242Z","iopub.execute_input":"2025-07-27T14:53:41.640576Z","iopub.status.idle":"2025-07-27T14:54:22.611506Z","shell.execute_reply.started":"2025-07-27T14:53:41.640548Z","shell.execute_reply":"2025-07-27T14:54:22.610436Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"import os\n\nprint(os.listdir(test_dir))  # test_dir 内のファイル一覧を表示\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:04:21.980403Z","iopub.execute_input":"2025-07-27T15:04:21.980715Z","iopub.status.idle":"2025-07-27T15:04:21.98707Z","shell.execute_reply.started":"2025-07-27T15:04:21.980694Z","shell.execute_reply":"2025-07-27T15:04:21.98597Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"import os\n\ntest1_dir = '/kaggle/working/test1'  # 正しいパスに応じて調整\ntest_image_files = [f for f in os.listdir(test1_dir) if f.endswith('.jpg')]\n\nprint(\"Test image count:\", len(test_image_files))\nprint(\"Example test image:\", test_image_files[:5])\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:04:57.263158Z","iopub.execute_input":"2025-07-27T15:04:57.263522Z","iopub.status.idle":"2025-07-27T15:04:57.280151Z","shell.execute_reply.started":"2025-07-27T15:04:57.263494Z","shell.execute_reply":"2025-07-27T15:04:57.279116Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"import tensorflow as tf\nimport numpy as np\nimport os\nfrom tensorflow.keras.preprocessing import image\n\n# モデルと画像サイズ（事前に定義済みのものに合わせて）\nimg_size = (128, 128)  # または (150,150) や (224,224) など\ntest_dir = '/kaggle/working/test1'  # 適宜変更\nmodel_path = '/kaggle/working/your_model.h5'  # 保存したモデルのパス\n\n# モデル読み込み\nmodel = tf.keras.models.load_model(model_path)\n\n# 推論対象画像のパスを取得\ntest_image_files = sorted([f for f in os.listdir(test_dir) if f.endswith('.jpg')])\ntest_image_paths = [os.path.join(test_dir, fname) for fname in test_image_files]\n\n# 推論関数\ndef preprocess_image(path):\n    img = image.load_img(path, target_size=img_size)\n    img_array = image.img_to_array(img)\n    img_array = np.expand_dims(img_array, axis=0)\n    img_array /= 255.0  # 正規化\n    return img_array\n\n# 推論結果格納用\nresults = []\n\nfor path in test_image_paths:\n    img_tensor = preprocess_image(path)\n    pred = model.predict(img_tensor)[0][0]\n    label = 'dog' if pred > 0.5 else 'cat'\n    results.append((os.path.basename(path), pred, label))\n\n# 結果表示（上位5件）\nfor name, score, label in results[:5]:\n    print(f\"{name}: {label} ({score:.4f})\")\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:05:36.174622Z","iopub.execute_input":"2025-07-27T15:05:36.175007Z","iopub.status.idle":"2025-07-27T15:05:36.242055Z","shell.execute_reply.started":"2025-07-27T15:05:36.174979Z","shell.execute_reply":"2025-07-27T15:05:36.240763Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"model.save('/kaggle/working/my_model.h5')  # 適宜パスは変更\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:06:10.183005Z","iopub.execute_input":"2025-07-27T15:06:10.183337Z","iopub.status.idle":"2025-07-27T15:06:10.388956Z","shell.execute_reply.started":"2025-07-27T15:06:10.183314Z","shell.execute_reply":"2025-07-27T15:06:10.387969Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"model_path = '/kaggle/working/my_model.h5'\nmodel = tf.keras.models.load_model(model_path)\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:06:17.893344Z","iopub.execute_input":"2025-07-27T15:06:17.893655Z","iopub.status.idle":"2025-07-27T15:06:18.027562Z","shell.execute_reply.started":"2025-07-27T15:06:17.893634Z","shell.execute_reply":"2025-07-27T15:06:18.026596Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"import os\n\nprint(os.listdir('/kaggle/working'))  # → モデルファイルがあるか確認\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:06:28.782605Z","iopub.execute_input":"2025-07-27T15:06:28.782965Z","iopub.status.idle":"2025-07-27T15:06:28.789572Z","shell.execute_reply.started":"2025-07-27T15:06:28.782939Z","shell.execute_reply":"2025-07-27T15:06:28.788455Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"model_path = '/kaggle/working/dog_cat_model.h5'\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:06:49.460454Z","iopub.execute_input":"2025-07-27T15:06:49.460778Z","iopub.status.idle":"2025-07-27T15:06:49.465544Z","shell.execute_reply.started":"2025-07-27T15:06:49.460753Z","shell.execute_reply":"2025-07-27T15:06:49.464627Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"# 保存\nmodel.save('/kaggle/working/dog_cat_model.h5')\n\n# 読み込み\nmodel = tf.keras.models.load_model('/kaggle/working/dog_cat_model.h5')\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:08:55.07142Z","iopub.execute_input":"2025-07-27T15:08:55.071771Z","iopub.status.idle":"2025-07-27T15:08:55.512409Z","shell.execute_reply.started":"2025-07-27T15:08:55.071747Z","shell.execute_reply":"2025-07-27T15:08:55.511386Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"IMG_SIZE = (128, 128)\n\ndef preprocess_image(path):\n    img = tf.io.read_file(path)\n    img = tf.image.decode_jpeg(img, channels=3)\n    img = tf.image.resize(img, IMG_SIZE)\n    img = img / 255.0\n    return img\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:09:29.916776Z","iopub.execute_input":"2025-07-27T15:09:29.917665Z","iopub.status.idle":"2025-07-27T15:09:29.9232Z","shell.execute_reply.started":"2025-07-27T15:09:29.917628Z","shell.execute_reply":"2025-07-27T15:09:29.922226Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"# test ディレクトリの画像ファイルパスを取得\ntest_dir = '/kaggle/working/test'  # 適宜パスを変更\ntest_images = sorted([\n    os.path.join(test_dir, fname) \n    for fname in os.listdir(test_dir) if fname.endswith('.jpg')\n])\n\n# tf.data.Dataset に変換\ntest_ds = tf.data.Dataset.from_tensor_slices(test_images)\ntest_ds = test_ds.map(preprocess_image)\ntest_ds = test_ds.batch(32)\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:09:39.520024Z","iopub.execute_input":"2025-07-27T15:09:39.520366Z","iopub.status.idle":"2025-07-27T15:09:39.608898Z","shell.execute_reply.started":"2025-07-27T15:09:39.52034Z","shell.execute_reply":"2025-07-27T15:09:39.606974Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"test_images = [str(path) for path in test_images]  # ← 明示的に str に変換\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:10:14.660802Z","iopub.execute_input":"2025-07-27T15:10:14.661145Z","iopub.status.idle":"2025-07-27T15:10:14.665815Z","shell.execute_reply.started":"2025-07-27T15:10:14.661123Z","shell.execute_reply":"2025-07-27T15:10:14.664848Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"IMG_SIZE = (128, 128)\n\ndef preprocess_image(path):\n    img = tf.io.read_file(path)\n    img = tf.image.decode_jpeg(img, channels=3)\n    img = tf.image.resize(img, IMG_SIZE)\n    img = img / 255.0\n    return img\n\n# パス読み込み・str変換\ntest_dir = '/kaggle/working/test'\ntest_images = sorted([\n    os.path.join(test_dir, fname) \n    for fname in os.listdir(test_dir) if fname.endswith('.jpg')\n])\ntest_images = [str(p) for p in test_images]  # ✅ ここが重要\n\n# Dataset に変換\ntest_ds = tf.data.Dataset.from_tensor_slices(test_images)\ntest_ds = test_ds.map(preprocess_image)\ntest_ds = test_ds.batch(32)\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:11:31.361332Z","iopub.execute_input":"2025-07-27T15:11:31.361849Z","iopub.status.idle":"2025-07-27T15:11:31.411876Z","shell.execute_reply.started":"2025-07-27T15:11:31.361817Z","shell.execute_reply":"2025-07-27T15:11:31.410259Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"import os\n\ntest_dir = '/kaggle/working/test'\n\n# パスのリスト作成\ntest_images = sorted([\n    os.path.join(test_dir, fname) \n    for fname in os.listdir(test_dir) \n    if fname.endswith('.jpg')\n])\n\n# 念のため明示的に文字列化\ntest_images = [str(p) for p in test_images]\n\n# 再確認\nprint(type(test_images[0]))  # str になるはず\nprint(test_images[:5])\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:12:01.515852Z","iopub.execute_input":"2025-07-27T15:12:01.516242Z","iopub.status.idle":"2025-07-27T15:12:01.540438Z","shell.execute_reply.started":"2025-07-27T15:12:01.516217Z","shell.execute_reply":"2025-07-27T15:12:01.539193Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"test_dir = '/kaggle/working/test1'  # 修正\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:12:33.570292Z","iopub.execute_input":"2025-07-27T15:12:33.570618Z","iopub.status.idle":"2025-07-27T15:12:33.575505Z","shell.execute_reply.started":"2025-07-27T15:12:33.570593Z","shell.execute_reply":"2025-07-27T15:12:33.574578Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"test_images = sorted([\n    os.path.join(test_dir, fname)\n    for fname in os.listdir(test_dir)\n    if fname.endswith('.jpg')\n])\n\nprint(f\"✅ test_images loaded: {len(test_images)} files\")\nprint(test_images[:5])  # 最初の5枚を確認\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:12:42.050752Z","iopub.execute_input":"2025-07-27T15:12:42.0511Z","iopub.status.idle":"2025-07-27T15:12:42.083223Z","shell.execute_reply.started":"2025-07-27T15:12:42.051076Z","shell.execute_reply":"2025-07-27T15:12:42.082115Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"IMG_SIZE = (128, 128)  # 学習時と合わせる\n\ndef preprocess_image(path):\n    img = tf.io.read_file(path)\n    img = tf.image.decode_jpeg(img, channels=3)\n    img = tf.image.resize(img, IMG_SIZE)\n    img = img / 255.0\n    return img\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:13:30.734736Z","iopub.execute_input":"2025-07-27T15:13:30.735121Z","iopub.status.idle":"2025-07-27T15:13:30.741008Z","shell.execute_reply.started":"2025-07-27T15:13:30.735093Z","shell.execute_reply":"2025-07-27T15:13:30.739886Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"test_ds = tf.data.Dataset.from_tensor_slices(test_images)\ntest_ds = test_ds.map(lambda x: preprocess_image(x))\ntest_ds = test_ds.batch(32)\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:13:39.551236Z","iopub.execute_input":"2025-07-27T15:13:39.551551Z","iopub.status.idle":"2025-07-27T15:13:39.614701Z","shell.execute_reply.started":"2025-07-27T15:13:39.551528Z","shell.execute_reply":"2025-07-27T15:13:39.613686Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"preds = model.predict(test_ds)\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:15:23.89453Z","iopub.execute_input":"2025-07-27T15:15:23.894835Z","iopub.status.idle":"2025-07-27T15:16:17.046333Z","shell.execute_reply.started":"2025-07-27T15:15:23.894816Z","shell.execute_reply":"2025-07-27T15:16:17.045309Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"labels = ['cat' if p < 0.5 else 'dog' for p in preds.flatten()]\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:16:46.842789Z","iopub.execute_input":"2025-07-27T15:16:46.843627Z","iopub.status.idle":"2025-07-27T15:16:46.871119Z","shell.execute_reply.started":"2025-07-27T15:16:46.8436Z","shell.execute_reply":"2025-07-27T15:16:46.870134Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"df.head()\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2025-07-27T15:18:05.844229Z","iopub.execute_input":"2025-07-27T15:18:05.844526Z","iopub.status.idle":"2025-07-27T15:18:05.879326Z","shell.execute_reply.started":"2025-07-27T15:18:05.844506Z","shell.execute_reply":"2025-07-27T15:18:05.878471Z"}},"outputs":[],"execution_count":null}]}