{"metadata":{"kernelspec":{"language":"python","display_name":"Python 3","name":"python3"},"language_info":{"name":"python","version":"3.10.14","mimetype":"text/x-python","codemirror_mode":{"name":"ipython","version":3},"pygments_lexer":"ipython3","nbconvert_exporter":"python","file_extension":".py"},"kaggle":{"accelerator":"none","dataSources":[{"sourceId":21755,"databundleVersionId":1475600,"sourceType":"competition"}],"dockerImageVersionId":30804,"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":"2024-12-17T17:02:36.055930Z","iopub.execute_input":"2024-12-17T17:02:36.056413Z","iopub.status.idle":"2024-12-17T17:02:43.500112Z","shell.execute_reply.started":"2024-12-17T17:02:36.056366Z","shell.execute_reply":"2024-12-17T17:02:43.498834Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"import tensorflow as tf\nfrom tensorflow.keras import layers\nimport numpy as np\nfrom kaggle_datasets import KaggleDatasets\nimport os\nfrom PIL import Image\nimport zipfile\n\n# Setup TPU atau Strategy Default\ntry:\n    tpu = tf.distribute.cluster_resolver.TPUClusterResolver()\n    tf.config.experimental_connect_to_cluster(tpu)\n    tf.tpu.experimental.initialize_tpu_system(tpu)\n    strategy = tf.distribute.TPUStrategy(tpu)\nexcept Exception as e:\n    print(\"TPU not found, switching to default strategy\")\n    strategy = tf.distribute.get_strategy()\nprint(\"Number of Replicas:\", strategy.num_replicas_in_sync)\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-17T17:03:19.624975Z","iopub.execute_input":"2024-12-17T17:03:19.625388Z","iopub.status.idle":"2024-12-17T17:03:34.164349Z","shell.execute_reply.started":"2024-12-17T17:03:19.625354Z","shell.execute_reply":"2024-12-17T17:03:34.162537Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"# Path Dataset Kaggle\nGCS_PATH = KaggleDatasets().get_gcs_path()\nMONET_FILENAMES = tf.io.gfile.glob(GCS_PATH + '/monet_tfrec/*.tfrec')\nPHOTO_FILENAMES = tf.io.gfile.glob(GCS_PATH + '/photo_tfrec/*.tfrec')\n\n# Fungsi untuk Decode Image dan Normalisasi\ndef decode_image(image):\n    image = tf.image.decode_jpeg(image, channels=3)\n    image = tf.image.resize(image, [256, 256])\n    return (tf.cast(image, tf.float32) / 127.5) - 1\n\ndef read_tfrecord(example):\n    format = {\"image\": tf.io.FixedLenFeature([], tf.string)}\n    example = tf.io.parse_single_example(example, format)\n    return decode_image(example['image'])\n\ndef load_dataset(filepaths):\n    return (tf.data.TFRecordDataset(filepaths)\n            .map(read_tfrecord, num_parallel_calls=tf.data.AUTOTUNE)\n            .batch(1)\n            .prefetch(tf.data.AUTOTUNE))\n\n# Load Dataset\nmonet_ds = load_dataset(MONET_FILENAMES)\nphoto_ds = load_dataset(PHOTO_FILENAMES)\n","metadata":{"trusted":true},"outputs":[],"execution_count":null},{"cell_type":"code","source":"def create_generator():\n    inputs = layers.Input(shape=[256, 256, 3])\n    x = inputs\n    down_stack = [64, 128, 256]\n    up_stack = [128, 64, 3]\n\n    for filters in down_stack:\n        x = layers.Conv2D(filters, 4, strides=2, padding='same', activation='relu')(x)\n    for filters in up_stack:\n        x = layers.Conv2DTranspose(filters, 4, strides=2, padding='same', activation='relu' if filters != 3 else 'tanh')(x)\n    return tf.keras.Model(inputs, x)\n\ndef create_discriminator():\n    inputs = layers.Input(shape=[256, 256, 3])\n    x = layers.Conv2D(64, 4, strides=2, padding='same', activation='relu')(inputs)\n    x = layers.Conv2D(128, 4, strides=2, padding='same')(x)\n    x = layers.Conv2D(1, 4, strides=1, padding='same')(x)\n    return tf.keras.Model(inputs, x)\n","metadata":{"trusted":true},"outputs":[],"execution_count":null},{"cell_type":"code","source":"class CycleGAN(tf.keras.Model):\n    def __init__(self, gen_monet, gen_photo):\n        super(CycleGAN, self).__init__()\n        self.gen_monet = gen_monet\n        self.gen_photo = gen_photo\n\n    def compile(self, optimizer, loss_fn):\n        super(CycleGAN, self).compile()\n        self.optimizer = optimizer\n        self.loss_fn = loss_fn\n\n    def train_step(self, batch):\n        real_photo, real_monet = batch\n\n        with tf.GradientTape() as tape:\n            # Generasi\n            fake_monet = self.gen_monet(real_photo, training=True)\n            fake_photo = self.gen_photo(real_monet, training=True)\n            # Loss sederhana (L1 Loss)\n            loss = self.loss_fn(real_monet, fake_monet) + self.loss_fn(real_photo, fake_photo)\n\n        gradients = tape.gradient(loss, self.gen_monet.trainable_variables + self.gen_photo.trainable_variables)\n        self.optimizer.apply_gradients(zip(gradients, self.gen_monet.trainable_variables + self.gen_photo.trainable_variables))\n        return {\"loss\": loss}\n","metadata":{"trusted":true},"outputs":[],"execution_count":null},{"cell_type":"code","source":"# Inisialisasi Generator\nwith strategy.scope():\n    gen_monet = create_generator()\n    gen_photo = create_generator()\n    cycle_gan = CycleGAN(gen_monet, gen_photo)\n    cycle_gan.compile(optimizer=tf.keras.optimizers.Adam(2e-4), loss_fn=tf.keras.losses.MeanAbsoluteError())\n\n# Latih Model\ncycle_gan.fit(tf.data.Dataset.zip((photo_ds, monet_ds)), epochs=50)\n","metadata":{"trusted":true},"outputs":[],"execution_count":null},{"cell_type":"code","source":"OUTPUT_DIR = './images_submission'\nos.makedirs(OUTPUT_DIR, exist_ok=True)\n\n# Fungsi Simpan Gambar\ndef save_images(generator, dataset, output_dir, num_images=7000):\n    index = 0\n    for img in dataset:\n        if index >= num_images: break\n        fake_img = generator(img, training=False).numpy()[0]\n        fake_img = (fake_img * 127.5 + 127.5).astype(np.uint8)\n        Image.fromarray(fake_img).save(f\"{output_dir}/image_{index:05d}.png\")\n        index += 1\n\n# Simpan Gambar dan Buat Zip\nsave_images(gen_monet, photo_ds, OUTPUT_DIR, num_images=7000)\nwith zipfile.ZipFile('images.zip', 'w') as zipf:\n    for file in os.listdir(OUTPUT_DIR):\n        zipf.write(os.path.join(OUTPUT_DIR, file), arcname=file)\n\nprint(\"Submission created: images.zip\")\n","metadata":{"trusted":true},"outputs":[],"execution_count":null},{"cell_type":"code","source":"","metadata":{"trusted":true},"outputs":[],"execution_count":null},{"cell_type":"code","source":"","metadata":{"trusted":true},"outputs":[],"execution_count":null}]}