Computer_Vision/Chapter05/Facial_keypoints_detection.ipynb

697 lines
174 KiB
Plaintext
Raw Normal View History

2024-02-13 03:34:51 +01:00
{
"nbformat": 4,
"nbformat_minor": 0,
"metadata": {
"colab": {
"name": "Facial_keypoints_detection.ipynb",
"provenance": [],
"include_colab_link": true
},
"kernelspec": {
"name": "python3",
"display_name": "Python 3"
},
"accelerator": "GPU",
"widgets": {
"application/vnd.jupyter.widget-state+json": {
"83ce203e54a24522a366e4dca4021ee4": {
"model_module": "@jupyter-widgets/controls",
"model_name": "HBoxModel",
"state": {
"_view_name": "HBoxView",
"_dom_classes": [],
"_model_name": "HBoxModel",
"_view_module": "@jupyter-widgets/controls",
"_model_module_version": "1.5.0",
"_view_count": null,
"_view_module_version": "1.5.0",
"box_style": "",
"layout": "IPY_MODEL_ed7edd8f643b446189fc8c62d93e3194",
"_model_module": "@jupyter-widgets/controls",
"children": [
"IPY_MODEL_defdbc0c82e84ba39b2347b393d93ced",
"IPY_MODEL_27b0a36b827e4be6ba7fa7fa87bcbe61"
]
}
},
"ed7edd8f643b446189fc8c62d93e3194": {
"model_module": "@jupyter-widgets/base",
"model_name": "LayoutModel",
"state": {
"_view_name": "LayoutView",
"grid_template_rows": null,
"right": null,
"justify_content": null,
"_view_module": "@jupyter-widgets/base",
"overflow": null,
"_model_module_version": "1.2.0",
"_view_count": null,
"flex_flow": null,
"width": null,
"min_width": null,
"border": null,
"align_items": null,
"bottom": null,
"_model_module": "@jupyter-widgets/base",
"top": null,
"grid_column": null,
"overflow_y": null,
"overflow_x": null,
"grid_auto_flow": null,
"grid_area": null,
"grid_template_columns": null,
"flex": null,
"_model_name": "LayoutModel",
"justify_items": null,
"grid_row": null,
"max_height": null,
"align_content": null,
"visibility": null,
"align_self": null,
"height": null,
"min_height": null,
"padding": null,
"grid_auto_rows": null,
"grid_gap": null,
"max_width": null,
"order": null,
"_view_module_version": "1.2.0",
"grid_template_areas": null,
"object_position": null,
"object_fit": null,
"grid_auto_columns": null,
"margin": null,
"display": null,
"left": null
}
},
"defdbc0c82e84ba39b2347b393d93ced": {
"model_module": "@jupyter-widgets/controls",
"model_name": "FloatProgressModel",
"state": {
"_view_name": "ProgressView",
"style": "IPY_MODEL_24d0980decbc43b2a78ed7b5c660650e",
"_dom_classes": [],
"description": "100%",
"_model_name": "FloatProgressModel",
"bar_style": "success",
"max": 553433881,
"_view_module": "@jupyter-widgets/controls",
"_model_module_version": "1.5.0",
"value": 553433881,
"_view_count": null,
"_view_module_version": "1.5.0",
"orientation": "horizontal",
"min": 0,
"description_tooltip": null,
"_model_module": "@jupyter-widgets/controls",
"layout": "IPY_MODEL_6033f056a30844199f5546975b0df311"
}
},
"27b0a36b827e4be6ba7fa7fa87bcbe61": {
"model_module": "@jupyter-widgets/controls",
"model_name": "HTMLModel",
"state": {
"_view_name": "HTMLView",
"style": "IPY_MODEL_87be4736644541008033b5eeb72a68ff",
"_dom_classes": [],
"description": "",
"_model_name": "HTMLModel",
"placeholder": "",
"_view_module": "@jupyter-widgets/controls",
"_model_module_version": "1.5.0",
"value": " 528M/528M [00:12<00:00, 42.8MB/s]",
"_view_count": null,
"_view_module_version": "1.5.0",
"description_tooltip": null,
"_model_module": "@jupyter-widgets/controls",
"layout": "IPY_MODEL_f23cb6ba2c9e4e11af112eb00ae8b585"
}
},
"24d0980decbc43b2a78ed7b5c660650e": {
"model_module": "@jupyter-widgets/controls",
"model_name": "ProgressStyleModel",
"state": {
"_view_name": "StyleView",
"_model_name": "ProgressStyleModel",
"description_width": "initial",
"_view_module": "@jupyter-widgets/base",
"_model_module_version": "1.5.0",
"_view_count": null,
"_view_module_version": "1.2.0",
"bar_color": null,
"_model_module": "@jupyter-widgets/controls"
}
},
"6033f056a30844199f5546975b0df311": {
"model_module": "@jupyter-widgets/base",
"model_name": "LayoutModel",
"state": {
"_view_name": "LayoutView",
"grid_template_rows": null,
"right": null,
"justify_content": null,
"_view_module": "@jupyter-widgets/base",
"overflow": null,
"_model_module_version": "1.2.0",
"_view_count": null,
"flex_flow": null,
"width": null,
"min_width": null,
"border": null,
"align_items": null,
"bottom": null,
"_model_module": "@jupyter-widgets/base",
"top": null,
"grid_column": null,
"overflow_y": null,
"overflow_x": null,
"grid_auto_flow": null,
"grid_area": null,
"grid_template_columns": null,
"flex": null,
"_model_name": "LayoutModel",
"justify_items": null,
"grid_row": null,
"max_height": null,
"align_content": null,
"visibility": null,
"align_self": null,
"height": null,
"min_height": null,
"padding": null,
"grid_auto_rows": null,
"grid_gap": null,
"max_width": null,
"order": null,
"_view_module_version": "1.2.0",
"grid_template_areas": null,
"object_position": null,
"object_fit": null,
"grid_auto_columns": null,
"margin": null,
"display": null,
"left": null
}
},
"87be4736644541008033b5eeb72a68ff": {
"model_module": "@jupyter-widgets/controls",
"model_name": "DescriptionStyleModel",
"state": {
"_view_name": "StyleView",
"_model_name": "DescriptionStyleModel",
"description_width": "",
"_view_module": "@jupyter-widgets/base",
"_model_module_version": "1.5.0",
"_view_count": null,
"_view_module_version": "1.2.0",
"_model_module": "@jupyter-widgets/controls"
}
},
"f23cb6ba2c9e4e11af112eb00ae8b585": {
"model_module": "@jupyter-widgets/base",
"model_name": "LayoutModel",
"state": {
"_view_name": "LayoutView",
"grid_template_rows": null,
"right": null,
"justify_content": null,
"_view_module": "@jupyter-widgets/base",
"overflow": null,
"_model_module_version": "1.2.0",
"_view_count": null,
"flex_flow": null,
"width": null,
"min_width": null,
"border": null,
"align_items": null,
"bottom": null,
"_model_module": "@jupyter-widgets/base",
"top": null,
"grid_column": null,
"overflow_y": null,
"overflow_x": null,
"grid_auto_flow": null,
"grid_area": null,
"grid_template_columns": null,
"flex": null,
"_model_name": "LayoutModel",
"justify_items": null,
"grid_row": null,
"max_height": null,
"align_content": null,
"visibility": null,
"align_self": null,
"height": null,
"min_height": null,
"padding": null,
"grid_auto_rows": null,
"grid_gap": null,
"max_width": null,
"order": null,
"_view_module_version": "1.2.0",
"grid_template_areas": null,
"object_position": null,
"object_fit": null,
"grid_auto_columns": null,
"margin": null,
"display": null,
"left": null
}
}
}
}
},
"cells": [
{
"cell_type": "markdown",
"metadata": {
"id": "view-in-github",
"colab_type": "text"
},
"source": [
"<a href=\"https://colab.research.google.com/github/PacktPublishing/Hands-On-Computer-Vision-with-PyTorch/blob/master/Chapter05/Facial_keypoints_detection.ipynb\" target=\"_parent\"><img src=\"https://colab.research.google.com/assets/colab-badge.svg\" alt=\"Open In Colab\"/></a>"
]
},
{
"cell_type": "code",
"metadata": {
"id": "mXJgVPnkWHmG"
},
"source": [
"import torchvision\n",
"import torch.nn as nn\n",
"import torch\n",
"import torch.nn.functional as F\n",
"from torchvision import transforms, models, datasets\n",
"from torchsummary import summary\n",
"import numpy as np, pandas as pd, os, glob\n",
"from mpl_toolkits.mplot3d import Axes3D\n",
"import matplotlib.pyplot as plt\n",
"import matplotlib\n",
"import glob\n",
"from sklearn import cluster\n",
"device = 'cuda' if torch.cuda.is_available() else 'cpu'"
],
"execution_count": null,
"outputs": []
},
{
"cell_type": "code",
"metadata": {
"id": "q9l9gSyWWfbT",
"outputId": "416b717e-5358-45bb-e71c-51aa18b33fd9",
"colab": {
"base_uri": "https://localhost:8080/",
"height": 126
}
},
"source": [
"!git clone https://github.com/udacity/P1_Facial_Keypoints.git\n",
"!cd P1_Facial_Keypoints\n",
"root_dir = 'P1_Facial_Keypoints/data/training/'\n",
"all_img_paths = glob.glob(os.path.join(root_dir, '*.jpg'))\n",
"data = pd.read_csv('P1_Facial_Keypoints/data/training_frames_keypoints.csv')"
],
"execution_count": null,
"outputs": [
{
"output_type": "stream",
"text": [
"Cloning into 'P1_Facial_Keypoints'...\n",
"remote: Enumerating objects: 5984, done.\u001b[K\n",
"remote: Total 5984 (delta 0), reused 0 (delta 0), pack-reused 5984\u001b[K\n",
"Receiving objects: 100% (5984/5984), 329.49 MiB | 25.28 MiB/s, done.\n",
"Resolving deltas: 100% (126/126), done.\n",
"Checking out files: 100% (5803/5803), done.\n"
],
"name": "stdout"
}
]
},
{
"cell_type": "code",
"metadata": {
"id": "V8Trh0jHWhXZ"
},
"source": [
"from torch.utils.data import TensorDataset, DataLoader, Dataset\n",
"import cv2, numpy as np\n",
"from copy import deepcopy\n",
"class FacesData(Dataset):\n",
" def __init__(self, df):\n",
" super(FacesData).__init__()\n",
" self.df = df\n",
" self.normalize = transforms.Normalize(mean=[0.485, 0.456, 0.406],\n",
" std=[0.229, 0.224, 0.225])\n",
" def __len__(self): return len(self.df)\n",
" def __getitem__(self, ix):\n",
" img_path = 'P1_Facial_Keypoints/data/training/' + self.df.iloc[ix,0]\n",
" img = cv2.imread(img_path)/255.\n",
" kp = deepcopy(self.df.iloc[ix,1:].tolist())\n",
" kp_x = (np.array(kp[0::2])/img.shape[1]).tolist()\n",
" kp_y = (np.array(kp[1::2])/img.shape[0]).tolist()\n",
" kp2 = kp_x + kp_y\n",
" kp2 = torch.tensor(kp2) \n",
" img = self.preprocess_input(img)\n",
" return img, kp2\n",
" def preprocess_input(self, img):\n",
" img = cv2.resize(img, (224,224))\n",
" img = torch.tensor(img).permute(2,0,1)\n",
" img = self.normalize(img).float()\n",
" return img.to(device)\n",
" def load_img(self, ix):\n",
" img_path = 'P1_Facial_Keypoints/data/training/' + self.df.iloc[ix,0] \n",
" img = cv2.imread(img_path)\n",
" img =cv2.cvtColor(img, cv2.COLOR_BGR2RGB)/255.\n",
" img = cv2.resize(img, (224,224))\n",
" return img\n"
],
"execution_count": null,
"outputs": []
},
{
"cell_type": "code",
"metadata": {
"id": "7Eu9BYRmW1FI"
},
"source": [
"from sklearn.model_selection import train_test_split\n",
"\n",
"train, test = train_test_split(data, test_size=0.2, random_state=101)\n",
"train_dataset = FacesData(train.reset_index(drop=True))\n",
"test_dataset = FacesData(test.reset_index(drop=True))\n",
"\n",
"train_loader = DataLoader(train_dataset, batch_size=32)\n",
"test_loader = DataLoader(test_dataset, batch_size=32)"
],
"execution_count": null,
"outputs": []
},
{
"cell_type": "code",
"metadata": {
"id": "4lrg5GV2W1YE"
},
"source": [
"def get_model():\n",
" model = models.vgg16(pretrained=True)\n",
" for param in model.parameters():\n",
" param.requires_grad = False\n",
" model.avgpool = nn.Sequential( nn.Conv2d(512,512,3),\n",
" nn.MaxPool2d(2),\n",
" nn.Flatten())\n",
" model.classifier = nn.Sequential(\n",
" nn.Linear(2048, 512),\n",
" nn.ReLU(),\n",
" nn.Dropout(0.5),\n",
" nn.Linear(512, 136),\n",
" nn.Sigmoid()\n",
" )\n",
" criterion = nn.L1Loss()\n",
" optimizer = torch.optim.Adam(model.parameters(), lr=1e-4)\n",
" return model.to(device), criterion, optimizer"
],
"execution_count": null,
"outputs": []
},
{
"cell_type": "code",
"metadata": {
"id": "J896b_cXW9Al",
"outputId": "1cb07162-b294-4637-890c-4d2f789b3da4",
"colab": {
"base_uri": "https://localhost:8080/",
"height": 85,
"referenced_widgets": [
"83ce203e54a24522a366e4dca4021ee4",
"ed7edd8f643b446189fc8c62d93e3194",
"defdbc0c82e84ba39b2347b393d93ced",
"27b0a36b827e4be6ba7fa7fa87bcbe61",
"24d0980decbc43b2a78ed7b5c660650e",
"6033f056a30844199f5546975b0df311",
"87be4736644541008033b5eeb72a68ff",
"f23cb6ba2c9e4e11af112eb00ae8b585"
]
}
},
"source": [
"model, criterion, optimizer = get_model()"
],
"execution_count": null,
"outputs": [
{
"output_type": "stream",
"text": [
"Downloading: \"https://download.pytorch.org/models/vgg16-397923af.pth\" to /root/.cache/torch/hub/checkpoints/vgg16-397923af.pth\n"
],
"name": "stderr"
},
{
"output_type": "display_data",
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "83ce203e54a24522a366e4dca4021ee4",
"version_minor": 0,
"version_major": 2
},
"text/plain": [
"HBox(children=(FloatProgress(value=0.0, max=553433881.0), HTML(value='')))"
]
},
"metadata": {
"tags": []
}
},
{
"output_type": "stream",
"text": [
"\n"
],
"name": "stdout"
}
]
},
{
"cell_type": "code",
"metadata": {
"id": "40dLabQ-W-5-"
},
"source": [
"def train_batch(img, kps, model, optimizer, criterion):\n",
" model.train()\n",
" optimizer.zero_grad()\n",
" _kps = model(img.to(device))\n",
" loss = criterion(_kps, kps.to(device))\n",
" loss.backward()\n",
" optimizer.step()\n",
" return loss"
],
"execution_count": null,
"outputs": []
},
{
"cell_type": "code",
"metadata": {
"id": "64ae1xYpXA-k"
},
"source": [
"@torch.no_grad()\n",
"def validate_batch(img, kps, model, criterion):\n",
" model.eval()\n",
" _kps = model(img.to(device))\n",
" loss = criterion(_kps, kps.to(device))\n",
" return _kps, loss"
],
"execution_count": null,
"outputs": []
},
{
"cell_type": "code",
"metadata": {
"id": "UipGbp5LXGPC",
"outputId": "6f5fb07a-c3df-4d2f-bc20-5257515c1f5f",
"colab": {
"base_uri": "https://localhost:8080/",
"height": 926
}
},
"source": [
"train_loss, test_loss = [], []\n",
"n_epochs = 50\n",
"\n",
"for epoch in range(n_epochs):\n",
" print(f\" epoch {epoch+ 1} : 50\")\n",
" epoch_train_loss, epoch_test_loss = 0, 0\n",
" for ix, (img,kps) in enumerate(train_loader):\n",
" loss = train_batch(img, kps, model, optimizer, criterion)\n",
" epoch_train_loss += loss.item() \n",
" epoch_train_loss /= (ix+1)\n",
"\n",
" for ix,(img,kps) in enumerate(test_loader):\n",
" ps, loss = validate_batch(img, kps, model, criterion)\n",
" epoch_test_loss += loss.item() \n",
" epoch_test_loss /= (ix+1)\n",
"\n",
" train_loss.append(epoch_train_loss)\n",
" test_loss.append(epoch_test_loss)"
],
"execution_count": null,
"outputs": [
{
"output_type": "stream",
"text": [
" epoch 1 : 50\n",
" epoch 2 : 50\n",
" epoch 3 : 50\n",
" epoch 4 : 50\n",
" epoch 5 : 50\n",
" epoch 6 : 50\n",
" epoch 7 : 50\n",
" epoch 8 : 50\n",
" epoch 9 : 50\n",
" epoch 10 : 50\n",
" epoch 11 : 50\n",
" epoch 12 : 50\n",
" epoch 13 : 50\n",
" epoch 14 : 50\n",
" epoch 15 : 50\n",
" epoch 16 : 50\n",
" epoch 17 : 50\n",
" epoch 18 : 50\n",
" epoch 19 : 50\n",
" epoch 20 : 50\n",
" epoch 21 : 50\n",
" epoch 22 : 50\n",
" epoch 23 : 50\n",
" epoch 24 : 50\n",
" epoch 25 : 50\n",
" epoch 26 : 50\n",
" epoch 27 : 50\n",
" epoch 28 : 50\n",
" epoch 29 : 50\n",
" epoch 30 : 50\n",
" epoch 31 : 50\n",
" epoch 32 : 50\n",
" epoch 33 : 50\n",
" epoch 34 : 50\n",
" epoch 35 : 50\n",
" epoch 36 : 50\n",
" epoch 37 : 50\n",
" epoch 38 : 50\n",
" epoch 39 : 50\n",
" epoch 40 : 50\n",
" epoch 41 : 50\n",
" epoch 42 : 50\n",
" epoch 43 : 50\n",
" epoch 44 : 50\n",
" epoch 45 : 50\n",
" epoch 46 : 50\n",
" epoch 47 : 50\n",
" epoch 48 : 50\n",
" epoch 49 : 50\n",
" epoch 50 : 50\n"
],
"name": "stdout"
}
]
},
{
"cell_type": "code",
"metadata": {
"id": "xx4zSPZGXI3L",
"outputId": "5a12c541-381f-42ef-f5d6-862c77d0b744",
"colab": {
"base_uri": "https://localhost:8080/",
"height": 295
}
},
"source": [
"epochs = np.arange(50)+1\n",
"import matplotlib.ticker as mtick\n",
"import matplotlib.pyplot as plt\n",
"import matplotlib.ticker as mticker\n",
"%matplotlib inline\n",
"plt.plot(epochs, train_loss, 'bo', label='Training loss')\n",
"plt.plot(epochs, test_loss, 'r', label='Test loss')\n",
"plt.title('Training and Test loss over increasing epochs')\n",
"plt.xlabel('Epochs')\n",
"plt.ylabel('Loss')\n",
"plt.legend()\n",
"plt.grid('off')\n",
"plt.show()"
],
"execution_count": null,
"outputs": [
{
"output_type": "display_data",
"data": {
"image/png": "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
"text/plain": [
"<Figure size 432x288 with 1 Axes>"
]
},
"metadata": {
"tags": [],
"needs_background": "light"
}
}
]
},
{
"cell_type": "code",
"metadata": {
"id": "BEOdMzvoXZkY",
"outputId": "69b005a7-0b8e-4338-8111-cd6e6e97b9d6",
"colab": {
"base_uri": "https://localhost:8080/",
"height": 311
}
},
"source": [
"ix = 0\n",
"plt.figure(figsize=(10,10))\n",
"plt.subplot(221)\n",
"plt.title('Original image')\n",
"im = test_dataset.load_img(ix)\n",
"plt.imshow(im)\n",
"plt.grid(False)\n",
"plt.subplot(222)\n",
"plt.title('Image with facial keypoints')\n",
"x, _ = test_dataset[ix]\n",
"plt.imshow(im)\n",
"kp = model(x[None]).flatten().detach().cpu()\n",
"plt.scatter(kp[:68]*224, kp[68:]*224, c='r')\n",
"plt.grid(False)\n",
"plt.show()"
],
"execution_count": null,
"outputs": [
{
"output_type": "display_data",
"data": {
"image/png": "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
"text/plain": [
"<Figure size 720x720 with 2 Axes>"
]
},
"metadata": {
"tags": [],
"needs_background": "light"
}
}
]
},
{
"cell_type": "code",
"metadata": {
"id": "ANmXl72oYO1o"
},
"source": [
""
],
"execution_count": null,
"outputs": []
}
]
}