{ "cells": [ { "cell_type": "code", "execution_count": 24, "metadata": { "id": "n-HmiNnY3rlq" }, "outputs": [], "source": [ "import tensorflow as tf\n", "from tensorflow import keras\n", "from tensorflow.keras import layers\n", "import numpy as np\n", "import matplotlib.pyplot as plt\n", "import os\n", "from IPython.display import clear_output\n", "from ipywidgets import interact, interactive, fixed, interact_manual\n", "import ipywidgets as widgets\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "# datos" ] }, { "cell_type": "code", "execution_count": 25, "metadata": { "id": "_i8vg7XP52TJ" }, "outputs": [], "source": [ "path = 'AnimeDCGAN'\n", "data_path = path +'/anime_faces'\n", "weights_path = path+'/weights'\n", "numpy_path= path+'/np_images'\n", "IMG_SIZE = (64,64)\n", "latent_dim = 100\n", "BATCH_SIZE = 128" ] }, { "cell_type": "code", "execution_count": 26, "metadata": { "colab": { "base_uri": "https://localhost:8080/" }, "id": "AuIxNNqO3rlq", "outputId": "3435fa8f-369c-4c5a-f917-20fd19f6bfc7" }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Found 63565 files belonging to 1 classes.\n" ] } ], "source": [ "dataset = keras.preprocessing.image_dataset_from_directory(\n", " data_path , label_mode=None, image_size=IMG_SIZE, batch_size=BATCH_SIZE\n", ")\n", "dataset = dataset.map(lambda x: x / 255.0)\n" ] }, { "cell_type": "code", "execution_count": 27, "metadata": { "colab": { "base_uri": "https://localhost:8080/", "height": 265 }, "id": "FsX7zHBI3rlr", "outputId": "88d7959a-4f9b-4b52-ed09-43191d6522c8" }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "(128, 64, 64, 3)\n" ] }, { "data": { "image/png": "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", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "for x in dataset:\n", " plt.axis(\"off\")\n", " plt.imshow((x.numpy() * 255).astype(\"int32\")[0])\n", " print(x.shape)\n", " break" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "# modelo" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## creacion" ] }, { "cell_type": "code", "execution_count": 28, "metadata": { "colab": { "base_uri": "https://localhost:8080/" }, "id": "9rOo5zYy3rlr", "outputId": "b4b20a55-7a10-4e19-9856-a24b75d22c89" }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Model: \"sequential_4\"\n", "_________________________________________________________________\n", " Layer (type) Output Shape Param # \n", "=================================================================\n", " conv2d_10 (Conv2D) (None, 32, 32, 64) 1728 \n", " \n", " leaky_re_lu_8 (LeakyReLU) (None, 32, 32, 64) 0 \n", " \n", " conv2d_11 (Conv2D) (None, 16, 16, 128) 73728 \n", " \n", " batch_normalization_14 (Bat (None, 16, 16, 128) 512 \n", " chNormalization) \n", " \n", " leaky_re_lu_9 (LeakyReLU) (None, 16, 16, 128) 0 \n", " \n", " conv2d_12 (Conv2D) (None, 8, 8, 256) 819200 \n", " \n", " batch_normalization_15 (Bat (None, 8, 8, 256) 1024 \n", " chNormalization) \n", " \n", " leaky_re_lu_10 (LeakyReLU) (None, 8, 8, 256) 0 \n", " \n", " conv2d_13 (Conv2D) (None, 4, 4, 512) 3276800 \n", " \n", " batch_normalization_16 (Bat (None, 4, 4, 512) 2048 \n", " chNormalization) \n", " \n", " leaky_re_lu_11 (LeakyReLU) (None, 4, 4, 512) 0 \n", " \n", " conv2d_14 (Conv2D) (None, 1, 1, 1) 8192 \n", " \n", " flatten_2 (Flatten) (None, 1) 0 \n", " \n", " activation_4 (Activation) (None, 1) 0 \n", " \n", "=================================================================\n", "Total params: 4,183,232\n", "Trainable params: 4,181,440\n", "Non-trainable params: 1,792\n", "_________________________________________________________________\n" ] } ], "source": [ "def discriminator():\n", " init = tf.keras.initializers.RandomNormal(stddev=0.02)\n", "\n", " model = keras.models.Sequential()\n", " \n", "\n", " model.add(layers.Conv2D(64,kernel_size=3,strides=2,padding='same',use_bias=False,input_shape=(IMG_SIZE[0],IMG_SIZE[1],3),kernel_initializer=init))\n", " model.add(layers.LeakyReLU(alpha=0.2)) \n", "\n", " model.add(layers.Conv2D(128,kernel_size=3,strides=2,padding='same',use_bias=False,kernel_initializer=init))\n", " model.add(layers.BatchNormalization())\n", " model.add(layers.LeakyReLU(alpha=0.2)) \n", "\n", " model.add(layers.Conv2D(256,kernel_size=5,strides=2,padding='same',use_bias=False,kernel_initializer=init))\n", " model.add(layers.BatchNormalization())\n", " model.add(layers.LeakyReLU(alpha=0.2))\n", "\n", " model.add(layers.Conv2D(512,kernel_size=5,strides=2,padding='same',use_bias=False,kernel_initializer=init))\n", " model.add(layers.BatchNormalization())\n", " model.add(layers.LeakyReLU(alpha=0.2)) \n", " \n", " model.add(layers.Conv2D(1,kernel_size=4,strides=1,padding='valid',use_bias=False,kernel_initializer=init))\n", " model.add(layers.Flatten())\n", " model.add(layers.Activation('sigmoid'))\n", " return model\n", "discriminator = discriminator()\n", "discriminator.summary()" ] }, { "cell_type": "code", "execution_count": 29, "metadata": { "colab": { "base_uri": "https://localhost:8080/" }, "id": "z_mste_43rls", "outputId": "e3df3669-e9b1-44ae-c3cd-888a40215cff" }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Model: \"sequential_5\"\n", "_________________________________________________________________\n", " Layer (type) Output Shape Param # \n", "=================================================================\n", " dense_2 (Dense) (None, 16384) 1654784 \n", " \n", " batch_normalization_17 (Bat (None, 16384) 65536 \n", " chNormalization) \n", " \n", " re_lu_8 (ReLU) (None, 16384) 0 \n", " \n", " reshape_2 (Reshape) (None, 4, 4, 1024) 0 \n", " \n", " conv2d_transpose_8 (Conv2DT (None, 8, 8, 512) 13107200 \n", " ranspose) \n", " \n", " batch_normalization_18 (Bat (None, 8, 8, 512) 2048 \n", " chNormalization) \n", " \n", " re_lu_9 (ReLU) (None, 8, 8, 512) 0 \n", " \n", " conv2d_transpose_9 (Conv2DT (None, 16, 16, 256) 3276800 \n", " ranspose) \n", " \n", " batch_normalization_19 (Bat (None, 16, 16, 256) 1024 \n", " chNormalization) \n", " \n", " re_lu_10 (ReLU) (None, 16, 16, 256) 0 \n", " \n", " conv2d_transpose_10 (Conv2D (None, 32, 32, 128) 294912 \n", " Transpose) \n", " \n", " batch_normalization_20 (Bat (None, 32, 32, 128) 512 \n", " chNormalization) \n", " \n", " re_lu_11 (ReLU) (None, 32, 32, 128) 0 \n", " \n", " conv2d_transpose_11 (Conv2D (None, 64, 64, 3) 3456 \n", " Transpose) \n", " \n", " activation_5 (Activation) (None, 64, 64, 3) 0 \n", " \n", "=================================================================\n", "Total params: 18,406,272\n", "Trainable params: 18,371,712\n", "Non-trainable params: 34,560\n", "_________________________________________________________________\n" ] } ], "source": [ "def generator():\n", " init = tf.keras.initializers.RandomNormal(stddev=0.02)\n", "\n", " model = keras.models.Sequential()\n", " \n", " model.add(layers.Dense(4*4*1024,kernel_initializer=init,input_dim=latent_dim))\n", " model.add(layers.BatchNormalization())\n", " model.add(layers.ReLU())\n", " model.add(layers.Reshape((4,4,1024))) \n", "\n", " \n", " model.add(layers.Conv2DTranspose(512,kernel_size=5,strides=2,padding='same',use_bias=False,kernel_initializer=init))\n", " model.add(layers.BatchNormalization())\n", " model.add(layers.ReLU()) \n", " \n", " model.add(layers.Conv2DTranspose(256,kernel_size=5,strides=2,padding='same',use_bias=False,kernel_initializer=init))\n", " model.add(layers.BatchNormalization())\n", " model.add(layers.ReLU()) \n", " \n", " model.add(layers.Conv2DTranspose(128,kernel_size=3,strides=2,padding='same',use_bias=False,kernel_initializer=init))\n", " model.add(layers.BatchNormalization())\n", " model.add(layers.ReLU()) \n", "\n", " model.add(layers.Conv2DTranspose(3,kernel_size=3,strides=2,padding='same',use_bias=False,kernel_initializer=init))\n", " model.add(layers.Activation('tanh')) \n", " return model\n", "generator = generator()\n", "generator.summary()" ] }, { "cell_type": "code", "execution_count": 30, "metadata": { "id": "O0opsFYj3rlt" }, "outputs": [], "source": [ "class GAN(keras.Model):\n", " def __init__(self, discriminator, generator, latent_dim):\n", " super(GAN, self).__init__()\n", " self.discriminator = discriminator\n", " self.generator = generator\n", " self.latent_dim = latent_dim\n", " \n", "\n", " def compile(self, d_optimizer, g_optimizer, loss_fn):\n", " super(GAN, self).compile()\n", " self.d_optimizer = d_optimizer\n", " self.g_optimizer = g_optimizer\n", " self.loss_fn = loss_fn\n", " self.d_loss_metric = keras.metrics.Mean(name=\"d_loss\")\n", " self.g_loss_metric = keras.metrics.Mean(name=\"g_loss\")\n", "\n", " @property\n", " def metrics(self):\n", " return [self.d_loss_metric, self.g_loss_metric]\n", "\n", " def train_step(self, real_images):\n", " \n", " batch_size = tf.shape(real_images)[0]\n", " noise = tf.random.normal(shape=(batch_size, self.latent_dim))\n", "\n", " \n", " with tf.GradientTape() as disc_tape1:\n", " generated_images = self.generator(noise, training=True)\n", "\n", " real_output = self.discriminator(real_images, training=True)\n", " real_targets = tf.ones_like(real_output)\n", " d_loss = self.loss_fn(real_targets, real_output)\n", "\n", " gradients_of_disc1 = disc_tape1.gradient(d_loss, self.discriminator.trainable_variables)\n", " self.d_optimizer.apply_gradients(zip(gradients_of_disc1,self.discriminator.trainable_variables))\n", " \n", " \n", " with tf.GradientTape() as disc_tape2:\n", " fake_output = self.discriminator(generated_images, training=True)\n", " fake_targets = tf.zeros_like(fake_output)\n", " disc_loss2 = self.loss_fn(fake_targets, fake_output)\n", " gradients_of_disc2 = disc_tape2.gradient(disc_loss2, self.discriminator.trainable_variables)\n", " self.d_optimizer.apply_gradients(zip(gradients_of_disc2,self.discriminator.trainable_variables))\n", "\n", "\n", " with tf.GradientTape() as gen_tape:\n", " generated_images = self.generator(noise, training=True)\n", " fake_output = self.discriminator(generated_images, training=True)\n", " real_targets = tf.ones_like(fake_output)\n", " gen_loss = self.loss_fn(real_targets, fake_output)\n", "\n", " gradients_of_gen = gen_tape.gradient(gen_loss, self.generator.trainable_variables)\n", " self.g_optimizer.apply_gradients(zip(gradients_of_gen,self.generator.trainable_variables)) \n", "\n", " self.d_loss_metric.update_state(d_loss)\n", " self.g_loss_metric.update_state(gen_loss)\n", " return {\n", " \"d_loss\": self.d_loss_metric.result(),\n", " \"g_loss\": self.g_loss_metric.result(),\n", " }" ] }, { "cell_type": "code", "execution_count": 31, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Requirement already satisfied: pydot in c:\\users\\franz\\.conda\\envs\\tf-gpu\\lib\\site-packages (1.4.2)\n", "Requirement already satisfied: pyparsing>=2.1.4 in c:\\users\\franz\\.conda\\envs\\tf-gpu\\lib\\site-packages (from pydot) (3.0.7)\n", "Requirement already satisfied: pydotplus in c:\\users\\franz\\.conda\\envs\\tf-gpu\\lib\\site-packages (2.0.2)\n", "Requirement already satisfied: pyparsing>=2.0.1 in c:\\users\\franz\\.conda\\envs\\tf-gpu\\lib\\site-packages (from pydotplus) (3.0.7)\n", "Requirement already satisfied: graphviz in c:\\users\\franz\\.conda\\envs\\tf-gpu\\lib\\site-packages (0.19.1)\n" ] } ], "source": [ "! pip install pydot\n", "! pip install pydotplus\n", "! pip install graphviz" ] }, { "cell_type": "code", "execution_count": 32, "metadata": { "id": "AUbyezGK3rlu" }, "outputs": [], "source": [ "class GANMonitor(keras.callbacks.Callback):\n", " def __init__(self, num_img=3, latent_dim=100,path='generadas',test_vector=None):\n", " self.num_img = num_img\n", " self.latent_dim = latent_dim\n", " self.path = path\n", " \n", "\n", " if not os.path.exists(path):\n", " os.makedirs(path)\n", " if not os.path.exists(path+'/img_training_gen'):\n", " os.makedirs(path+'/img_training_gen')\n", " if not os.path.exists(path+'/weights_auto_save'):\n", " os.makedirs(path+'/weights_auto_save')\n", " if not os.path.exists(numpy_path):\n", " os.makedirs(numpy_path)\n", " \n", " if test_vector is None :\n", " self.random_latent_vectors = tf.random.normal(shape=(self.num_img, self.latent_dim))\n", " np.save(numpy_path+'/origen',self.random_latent_vectors )\n", " else :\n", " self.random_latent_vectors = test_vector\n", " def on_epoch_end(self, epoch, logs=None):\n", " clear_output(wait=True)\n", " if(epoch%10==0):\n", " self.model.save_weights(f'{self.path}/weights_auto_save/{epoch}', save_format='tf')\n", " \n", " generated_images = self.model.generator(self.random_latent_vectors)\n", " generated_images *= 255\n", " generated_images.numpy()\n", " for i in range(self.num_img):\n", " img = keras.preprocessing.image.array_to_img(generated_images[i])\n", " plt.imshow((generated_images[i].numpy()).astype(\"int32\"))\n", " img.save(f'{self.path}/img_training_gen/generated_img_{epoch}_{i}.png')\n", " plt.show()\n", " \n", " " ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## entrenamiento" ] }, { "cell_type": "code", "execution_count": 38, "metadata": { "colab": { "base_uri": "https://localhost:8080/" }, "id": "3AhjV0T_3rlu", "outputId": "a5cc1c5b-337d-4471-e96a-a1ab97062a9c" }, "outputs": [], "source": [ "gan = GAN(discriminator=discriminator, generator=generator, latent_dim=latent_dim)\n", "gan.compile(\n", " d_optimizer=tf.keras.optimizers.Adam(lr = 0.0002, beta_1 = 0.5, beta_2 = 0.999 ),\n", " g_optimizer=tf.keras.optimizers.Adam(lr = 0.0002, beta_1 = 0.5, beta_2 = 0.999 ),\n", " loss_fn=keras.losses.BinaryCrossentropy(),\n", ")\n", "callback = GANMonitor(1, path = path)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "# resultados modelo " ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "# load weights\n" ] }, { "cell_type": "code", "execution_count": 34, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "" ] }, "execution_count": 34, "metadata": {}, "output_type": "execute_result" } ], "source": [ "gan.load_weights(weights_path+'/weights')" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## img random " ] }, { "cell_type": "code", "execution_count": 39, "metadata": { "id": "0QPNo21R3rlv" }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "1/1 [==============================] - 0s 64ms/step\n" ] }, { "data": { "image/png": "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", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "test_vect = tf.random.normal(shape=(2, latent_dim))\n", "test = generator.predict(test_vect)\n", "original = test[0]\n", "plt.imshow(test[0])\n", "np.save(numpy_path+'/random',test_vect[0])" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## modificar imagen random" ] }, { "cell_type": "code", "execution_count": 40, "metadata": {}, "outputs": [], "source": [ "from ipywidgets import GridspecLayout,Button,Layout\n", "from matplotlib import pyplot as plt\n", "import ipywidgets as w\n", "from IPython.display import display, clear_output\n", "output = w.Output()\n", "\n", "\n", "\n", "def dict_to_arr(d): \n", " dictlist=[]\n", " for x in d.items():\n", " temp = x[1]\n", " dictlist.append(temp)\n", " return dictlist\n", "def on_button_clicked_random(): \n", " seed = tf.random.normal(shape=(2, latent_dim))[0]\n", " for i , s in enumerate(sliders):\n", " s.value = seed[i]\n", " return seed\n", "def create_grid(kwargs,latent_dim, columnas = 10):\n", " grid = GridspecLayout(10, 11)\n", " filas = latent_dim//columnas \n", " for i in range(filas):\n", " for j in range(columnas):\n", " if (i-1)*filas+(j-1) >= latent_dim:\n", " break\n", " grid[i, j] = sliders[(i-1)*10+(j-1)]\n", " return grid \n", "def update_chart(change):\n", " with output:\n", " clear_output()\n", " x = [s.value for s in sliders]\n", " test_vect = np.zeros(shape=(2, latent_dim))\n", " test_vect[0] = tf.convert_to_tensor(x, dtype=tf.float32)\n", " test = generator.predict(test_vect)\n", "\n", " f = plt.figure()\n", " f.add_subplot(1,2, 1)\n", " plt.imshow(test[0])\n", " f.add_subplot(1,2, 2)\n", " plt.imshow(original)\n", " plt.show(block=True)\n", " \n", " \n", "def funtion_to_sliders(sliders): \n", " for s in sliders:\n", " s.observe(update_chart, 'value')\n", " return sliders\n", "def guardar_numpy(b):\n", " with output:\n", " x = [s.value for s in sliders]\n", " x = np.array(x)\n", " np.save(numpy_path+'/modificada',x)\n", "\n", "seed =test_vect[0]\n", "\n", "kwargs = {'seed[{}]'.format(i) : \n", " widgets.FloatSlider( min = -1.0, \n", " max = 1.0, \n", " step = 0.01, \n", " value = seed[i]) \n", " for i in range(latent_dim)}\n", "\n", "sliders = dict_to_arr(kwargs)\n", "sliders = funtion_to_sliders(sliders)\n", "grid = create_grid(kwargs,latent_dim)\n", "\n", "guardar = widgets.Button(description=\"guardar\")\n", "guardar.on_click(guardar_numpy)\n", "\n", "random = widgets.Button(description=\"random\")\n", "random.on_click(on_button_clicked_random)" ] }, { "cell_type": "code", "execution_count": 41, "metadata": {}, "outputs": [ { "data": { "application/vnd.jupyter.widget-view+json": { "model_id": "a200b305cdf34114a943e120ed2ce3ec", "version_major": 2, "version_minor": 0 }, "text/plain": [ "VBox(children=(GridspecLayout(children=(FloatSlider(value=0.13039077818393707, layout=Layout(grid_area='widget…" ] }, "metadata": {}, "output_type": "display_data" } ], "source": [ "w.VBox([grid,output,guardar,random])" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "# train\n" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "colab": { "base_uri": "https://localhost:8080/", "height": 337 }, "id": "CGYGTWXi3rlv", "outputId": "0558b7d5-0dfd-477b-e5b1-866de9c4a249" }, "outputs": [], "source": [ "epochs = 100 \n", "training = gan.fit(\n", " dataset, epochs=epochs, callbacks=callback \n", ")" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "# save weights" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "id": "y2zjFEML3rlv" }, "outputs": [], "source": [ "gan.save_weights('weights/weights_new', save_format='tf')" ] } ], "metadata": { "accelerator": "GPU", "colab": { "collapsed_sections": [], "name": "SIMPLE_DCGAN", "provenance": [] }, "interpreter": { "hash": "3af8d5c17c834a5715d68deec2bf9936116d60d2d90b474f74600ac6ca4ca936" }, "kernelspec": { "display_name": "Python 3.10.1 64-bit", "language": "python", "name": "python3" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.10.0" }, "orig_nbformat": 4 }, "nbformat": 4, "nbformat_minor": 0 }