├── .gitignore ├── README.md ├── data ├── IMAGES_RAW.mat ├── images_org │ ├── image0.png │ ├── image1.png │ ├── image2.png │ ├── image3.png │ └── image4.png └── images_rao │ ├── image0.png │ ├── image1.png │ ├── image2.png │ ├── image3.png │ └── image4.png ├── dataset.py ├── dataset_test.py ├── docs ├── figures │ ├── end_stopping.png │ └── network.png └── images │ ├── u1_00.png │ ├── u1_01.png │ ├── u1_03.png │ ├── u1_06.png │ ├── u1_11.png │ ├── u1_17.png │ ├── u1_26.png │ ├── u1_27.png │ ├── u2_004.png │ ├── u2_007.png │ ├── u2_016.png │ ├── u2_023.png │ ├── u2_034.png │ └── u2_054.png ├── end_stopping.ipynb ├── main.py ├── model.py └── model_test.py /.gitignore: -------------------------------------------------------------------------------- 1 | __pycache__ 2 | 3 | .DS_Store 4 | ._.DS_Store 5 | 6 | .ipynb_checkpoints 7 | result 8 | 9 | data/images_brd 10 | saved* 11 | 12 | debug* -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Predictive Coding 2 | 3 | A third-party reimplementation of the paper: ["Predictive Coding in the Visual Cortex: a Functional Interpretation of Some Extra-classical Receptive-field Effects"](https://www.researchgate.net/publication/13103385_Predictive_Coding_in_the_Visual_Cortex_a_Functional_Interpretation_of_Some_Extra-classical_Receptive-field_Effects) by Rajesh P. N. Rao and Dana H. Ballard 4 | 5 | 6 | 7 | ## Network 8 | 9 | Network image from Rao's original paper: 10 | 11 | ![network](docs/figures/network.png) 12 | 13 | 14 | 15 | ## Results 16 | 17 | 18 | ### Network weights 19 | 20 | #### Level1 21 | 22 | ![](docs/images/u1_01.png)![](docs/images/u1_03.png)![](docs/images/u1_11.png)![](docs/images/u1_17.png)![](docs/images/u1_26.png)![](docs/images/u1_27.png) 23 | 24 | 25 | #### Level2 26 | ![](docs/images/u2_004.png)![](docs/images/u2_007.png)![](docs/images/u2_016.png)![](docs/images/u2_023.png)![](docs/images/u2_034.png)![](docs/images/u2_054.png) 27 | 28 | 29 | 30 | ### End stopping 31 | 32 | Visualization of the prediction errors (r - r^td) at the center level1 module with long and short bar image input. 33 | 34 | The prediction errors for the long bar should be much more smaller, they are not smaller compared with the original paper's result. 35 | 36 | 37 | 38 | ![end_stopping](docs/figures/end_stopping.png) 39 | 40 | -------------------------------------------------------------------------------- /data/IMAGES_RAW.mat: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/data/IMAGES_RAW.mat -------------------------------------------------------------------------------- /data/images_org/image0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/data/images_org/image0.png -------------------------------------------------------------------------------- /data/images_org/image1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/data/images_org/image1.png -------------------------------------------------------------------------------- /data/images_org/image2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/data/images_org/image2.png -------------------------------------------------------------------------------- /data/images_org/image3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/data/images_org/image3.png -------------------------------------------------------------------------------- /data/images_org/image4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/data/images_org/image4.png -------------------------------------------------------------------------------- /data/images_rao/image0.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/data/images_rao/image0.png -------------------------------------------------------------------------------- /data/images_rao/image1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/data/images_rao/image1.png -------------------------------------------------------------------------------- /data/images_rao/image2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/data/images_rao/image2.png -------------------------------------------------------------------------------- /data/images_rao/image3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/data/images_rao/image3.png -------------------------------------------------------------------------------- /data/images_rao/image4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/data/images_rao/image4.png -------------------------------------------------------------------------------- /dataset.py: -------------------------------------------------------------------------------- 1 | # -*- coding: utf-8 -*- 2 | import numpy as np 3 | import cv2 4 | 5 | 6 | class Dataset: 7 | def __init__(self, scale=10.0, shuffle=False, use_rao=True): 8 | self.load_images(scale, use_rao) 9 | 10 | if shuffle: 11 | indices = np.random.permutation(len(self.patches)) 12 | self.patches = self.patches[indices] 13 | 14 | self.mask = self.create_gauss_mask() 15 | 16 | def load_images(self, scale, use_rao): 17 | images = [] 18 | 19 | if use_rao: 20 | # Use images from the paper 21 | dir_name = "images_rao" 22 | else: 23 | dir_name = "images_org" 24 | 25 | for i in range(5): 26 | image = cv2.imread("data/{}/image{}.png".format(dir_name, i)) 27 | image = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY).astype(np.float32) 28 | images.append(image) 29 | images = np.array(images) 30 | self.load_sub(images, scale) 31 | 32 | def create_gauss_mask(self, sigma=0.4): 33 | """ Create gaussian mask. """ 34 | width = 16 35 | mask = [0.0] * (width * width) 36 | hw = width // 2 37 | for i in range(width): 38 | x = (i - hw) / float(hw) 39 | for j in range(width): 40 | y = (j - hw) / float(hw) 41 | r = np.sqrt(x*x + y*y) 42 | mask[j*width + i] = self.gauss(r, sigma=sigma) 43 | mask = np.array(mask) 44 | # Normalize 45 | mask = mask / np.max(mask) 46 | return mask 47 | 48 | def gauss(self, x, sigma): 49 | sigma_sq = sigma * sigma 50 | return 1.0 / np.sqrt(2.0 * np.pi * sigma_sq) * np.exp(-x*x/(2 * sigma_sq)) 51 | 52 | def load_sub(self, images, scale): 53 | self.images = images 54 | 55 | filtered_images = [] 56 | for image in images: 57 | filtered_image = self.apply_DoG_filter(image) 58 | filtered_images.append(filtered_image) 59 | 60 | self.filtered_images = filtered_images 61 | 62 | w = images.shape[2] 63 | h = images.shape[1] 64 | 65 | size_w = w // 26 66 | size_h = h // 16 67 | 68 | patches = np.empty((size_h * size_w * len(images), 16, 26), dtype=np.float32) 69 | 70 | for image_index, filtered_image in enumerate(filtered_images): 71 | for j in range(size_h): 72 | y = 16 * j 73 | for i in range(size_w): 74 | x = 26 * i 75 | patch = filtered_image[y:y+16, x:x+26] 76 | # (16, 26) 77 | # print(patch.shape) 78 | index = size_w*size_h*image_index + j*size_w + i 79 | patches[index] = patch 80 | 81 | patches = patches * scale 82 | self.patches = patches 83 | 84 | def get_images_from_patch(self, patch, use_mask=True): 85 | images = [] 86 | for i in range(3): 87 | x = 5 * i 88 | # Apply gaussian mask 89 | image = patch[:, x:x+16].reshape([-1]) 90 | if use_mask: 91 | image = image * self.mask 92 | images.append(image) 93 | return images 94 | 95 | def get_images(self, patch_index): 96 | patch = self.patches[patch_index] 97 | return self.get_images_from_patch(patch) 98 | 99 | def apply_DoG_filter(self, gray, ksize=(5,5), sigma1=1.3, sigma2=2.6): 100 | """ 101 | Apply difference of gaussian (DoG) filter detect edge of the image. 102 | """ 103 | g1 = cv2.GaussianBlur(gray, ksize, sigma1) 104 | g2 = cv2.GaussianBlur(gray, ksize, sigma2) 105 | return g1 - g2 106 | 107 | def get_bar_images(self, is_short): 108 | patch = self.get_bar_patch(is_short) 109 | return self.get_images_from_patch(patch, use_mask=True) 110 | 111 | def get_bar_patch(self, is_short): 112 | """ 113 | Get bar patch image for end stopping test. 114 | """ 115 | bar_patch = np.ones((16,26), dtype=np.float32) 116 | 117 | if is_short: 118 | bar_width = 6 119 | else: 120 | bar_width = 24 121 | bar_height = 2 122 | 123 | for x in range(bar_patch.shape[1]): 124 | for y in range(bar_patch.shape[0]): 125 | if x >= 26/2 - bar_width/2 and \ 126 | x < 26/2 + bar_width/2 and \ 127 | y >= 16/2 - bar_height/2 and \ 128 | y < 16/2 + bar_height/2: 129 | bar_patch[y,x] = -1.0 130 | 131 | # Sete scale with stddev of all patch images. 132 | scale = np.std(self.patches) 133 | # Original scaling value for bar 134 | bar_scale = 2.0 135 | return bar_patch * scale * bar_scale 136 | -------------------------------------------------------------------------------- /dataset_test.py: -------------------------------------------------------------------------------- 1 | # -*- coding: utf-8 -*- 2 | import numpy as np 3 | import unittest 4 | 5 | from dataset import Dataset 6 | 7 | class DatasetTest(unittest.TestCase): 8 | def test_init(self): 9 | dataset = Dataset(scale=10.0, shuffle=True) 10 | patch_size = 2375 11 | self.assertEqual(dataset.patches.shape, (patch_size,16,26)) 12 | 13 | images = dataset.get_images(0) 14 | bar_images_short = dataset.get_bar_images(is_short=True) 15 | bar_images_long = dataset.get_bar_images(is_short=False) 16 | 17 | for i in range(3): 18 | self.assertEqual(images[i].shape, (256,)) 19 | self.assertEqual(bar_images_short[i].shape, (256,)) 20 | self.assertEqual(bar_images_long[i].shape, (256,)) 21 | 22 | if __name__ == '__main__': 23 | unittest.main() 24 | -------------------------------------------------------------------------------- /docs/figures/end_stopping.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/figures/end_stopping.png -------------------------------------------------------------------------------- /docs/figures/network.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/figures/network.png -------------------------------------------------------------------------------- /docs/images/u1_00.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/images/u1_00.png -------------------------------------------------------------------------------- /docs/images/u1_01.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/images/u1_01.png -------------------------------------------------------------------------------- /docs/images/u1_03.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/images/u1_03.png -------------------------------------------------------------------------------- /docs/images/u1_06.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/images/u1_06.png -------------------------------------------------------------------------------- /docs/images/u1_11.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/images/u1_11.png -------------------------------------------------------------------------------- /docs/images/u1_17.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/images/u1_17.png -------------------------------------------------------------------------------- /docs/images/u1_26.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/images/u1_26.png -------------------------------------------------------------------------------- /docs/images/u1_27.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/images/u1_27.png -------------------------------------------------------------------------------- /docs/images/u2_004.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/images/u2_004.png -------------------------------------------------------------------------------- /docs/images/u2_007.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/images/u2_007.png -------------------------------------------------------------------------------- /docs/images/u2_016.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/images/u2_016.png -------------------------------------------------------------------------------- /docs/images/u2_023.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/images/u2_023.png -------------------------------------------------------------------------------- /docs/images/u2_034.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/images/u2_034.png -------------------------------------------------------------------------------- /docs/images/u2_054.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/miyosuda/predictive_coding/770c8c16ab8730cc63eb5a68b73a04918ed5b541/docs/images/u2_054.png -------------------------------------------------------------------------------- /end_stopping.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "code", 5 | "execution_count": 1, 6 | "metadata": {}, 7 | "outputs": [], 8 | "source": [ 9 | "import numpy as np\n", 10 | "import matplotlib.pyplot as plt\n", 11 | "%matplotlib inline" 12 | ] 13 | }, 14 | { 15 | "cell_type": "code", 16 | "execution_count": 2, 17 | "metadata": {}, 18 | "outputs": [ 19 | { 20 | "name": "stdout", 21 | "output_type": "stream", 22 | "text": [ 23 | "loaded: saved\n" 24 | ] 25 | } 26 | ], 27 | "source": [ 28 | "from dataset import Dataset\n", 29 | "from model import Model\n", 30 | "\n", 31 | "dataset = Dataset(scale=1.0)\n", 32 | "model = Model()\n", 33 | "model.load(\"saved\")" 34 | ] 35 | }, 36 | { 37 | "cell_type": "code", 38 | "execution_count": 3, 39 | "metadata": {}, 40 | "outputs": [], 41 | "source": [ 42 | "bar_images_short = dataset.get_bar_images(is_short=True)\n", 43 | "bar_images_long = dataset.get_bar_images(is_short=False)\n", 44 | "\n", 45 | "start_pos = 32\n", 46 | "end_pos = 64\n", 47 | "\n", 48 | "rs_short, r_tds_short, rh_short, error_tds_short = model.apply_images(bar_images_short, training=False)\n", 49 | "r_short = rs_short[start_pos:end_pos]\n", 50 | "r_td_short = r_tds_short[start_pos:end_pos]\n", 51 | "error_tds_short = error_tds_short[start_pos:end_pos]\n", 52 | "\n", 53 | "rs_long, r_tds_long, rh_long, error_tds_long = model.apply_images(bar_images_long, training=False)\n", 54 | "r_long = rs_long[start_pos:end_pos]\n", 55 | "r_td_long = r_tds_long[start_pos:end_pos]\n", 56 | "error_tds_long = error_tds_long[start_pos:end_pos]" 57 | ] 58 | }, 59 | { 60 | "cell_type": "code", 61 | "execution_count": 4, 62 | "metadata": {}, 63 | "outputs": [ 64 | { 65 | "data": { 66 | "image/png": "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\n", 67 | "text/plain": [ 68 | "
" 69 | ] 70 | }, 71 | "metadata": {}, 72 | "output_type": "display_data" 73 | } 74 | ], 75 | "source": [ 76 | "max_value = np.max([np.max(error_tds_long), np.max(error_tds_short)])\n", 77 | "min_value = np.min([np.min(error_tds_long), np.min(error_tds_short)])\n", 78 | "mid_value = (max_value + min_value) / 2\n", 79 | "value_range = max_value - min_value\n", 80 | "\n", 81 | "plt.figure(figsize=(12, 4)) # figureの縦横の大きさ\n", 82 | "\n", 83 | "plt.subplot(1,2,1)\n", 84 | "plt.title(\"r - r_td (short bar)\")\n", 85 | "plt.ylim([mid_value - (value_range/2) * 1.1, mid_value + (value_range/2) * 1.1])\n", 86 | "plt.stem(list(range(len(error_tds_short))), error_tds_short, label='short',\n", 87 | " markerfmt=',')\n", 88 | "\n", 89 | "plt.subplot(1,2,2)\n", 90 | "plt.title(\"r - r_td (long bar)\")\n", 91 | "plt.ylim([mid_value - (value_range/2) * 1.1, mid_value + (value_range/2) * 1.1])\n", 92 | "plt.stem(list(range(len(error_tds_long))), error_tds_long, label='long',\n", 93 | " markerfmt=',')\n", 94 | "plt.show()" 95 | ] 96 | }, 97 | { 98 | "cell_type": "code", 99 | "execution_count": 5, 100 | "metadata": {}, 101 | "outputs": [ 102 | { 103 | "data": { 104 | "image/png": "iVBORw0KGgoAAAANSUhEUgAAASwAAAD8CAYAAADNNJnuAAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAAALEgAACxIB0t1+/AAAADl0RVh0U29mdHdhcmUAbWF0cGxvdGxpYiB2ZXJzaW9uIDIuMi4yLCBodHRwOi8vbWF0cGxvdGxpYi5vcmcvhp/UCwAAFY9JREFUeJzt3X+QXWV9x/H3h00iJEI2gCAmTEHLMNNSq0yGWnWsFcWIlGhrO8FaQZhhlNJia8eBMiNOO85oaa3VOjhUU2nNgBalMjQI8QfDOCOUBAIGghIpSmJgTSGJSTDJZr/9457t3N2zP+597nPPPef6ec3c2fvjPOc8e+7Z7z7nOed5vooIzMya4KhBV8DMrFMOWGbWGA5YZtYYDlhm1hgOWGbWGA5YZtYYDlhm1hgOWGbWGA5YZtZXkkYkPSTpjl7XtSBHhTq1ZMmSGB0drXKTtSZp0FX4pTWsIzx2797N/v37ezqwVq1aFbt27epo2U2bNt0VEavmWewqYCtwXC/1gooD1ujoKB/4wAeq3GQljjoqraGaGrBSyjUhOKYGkZRyqduamJhIKleVG264oed17Nq1i40bN3a0rKQT5/l8BfB24GPAX/Zat0oDlpk1Q8YW6KeADwPH5lhZT31YklZJ+oGkbZKuzlEhMxu8iYmJjh7AiZI2tj0un1yHpAuAsYjYlKteyS0sSSPAZ4G3ANuBByTdHhGP5aqcmVUvIrppYe2KiJWzfPY64EJJ5wNHA8dJ+lJEvCe1br20sM4BtkXEkxFxCLgFWN3D+sysJiaD1nyPedZxTUSsiIjTgDXAt3sJVtBbwFoOPN32envxnpk1XI6A1Q9973QvzmkvB1i6dGm/N2dmGeQORhFxD3BPr+vppYW1Azi17fWK4r0pIuLGiFgZESuXLFnSw+bMrCrD2MJ6ADhD0um0AtUa4N1ZamVmAxMRtb3fLDlgRcS4pCuBu4ARYG1EPJqtZmY2MHUdCdBTH1ZErAfWZ6qLmdXEUAYsMxtODlhm1giD6lDvxNAGrCoHJKduq8pyVQ/QTjngUzt6U8qlbqsJ+yOHoet0N7Ph5RaWmTWCTwnNrFEcsMysMRywzKwxHLDMrBGGcmiOmQ0vt7DMrDEcsMysMRywzKwxHLDMrBFydrpLOhq4F3gRrXhza0Rcl7o+BywzK8nYwjoIvCki9klaCHxX0p0RcV/KyhoRsKoc7JtSbsGCtN1YZbmRkZGkbVU52PfIkSNJ2xofH6+kTC/l6nqbwGxyBaxorWhf8XJh8UheeU+JVM1sOOWc013SiKTNwBiwISLuT62XA5aZTdFpsCoC1qyZn9vWdyQiXkUrUc05ks5KrVsjTgnNrFqZMj9PX+duSd8BVgFbUuqV3MKSdKqk70h6TNKjkq5KXZeZ1cvExERHj/lIeomk0eL5McBbgMdT69VLC2sc+FBEPCjpWGCTpA0R8VgP6zSzGsh4lfAU4CZJI7QaSF+JiDtSV9ZLmq+dwM7i+c8lbaWVqt4By6zBck7gFxGPAK/OsjIy9WFJOo1WpUq9/05Vb9Y8db3TveerhJJeDHwV+GBE7J3+uVPVmzXPMKaqp7hz9avAuoj4Wp4qmdmg1bWFlRyw1LoF+gvA1oj4ZL4qmdkg1XkCv15OCV8H/AnwJkmbi8f5meplZgM0dKeEEfFdIG2gmZnV2tCdEprZ8HLA6kGV6eMXLlxYSRmAY445JqncokWLui6TWsfU/ZjSB3L48OGkbR06dKjrMi+88ELStlJnr0j53VKCRmr9cmy7Co0IWGZWnTp3ujtgmVmJW1hm1hgOWGbWGA5YZtYIg7rHqhMOWGZW4oBlZo3hq4Rm1hhuYZlZI9S5D8tZc8ysJNfg59y5H9zCMrOSjC2srLkfHLDMrCTjnO5Zcz9UHrCqSjufmgY+ZZBw6tTPqeUWL17cdZnUgdapKe5T0s6nDkg+cOBA12VSB3Xv378/qVxKABhUP1KXYwlPlLSx7fWNEXHjTAvOlfuhU25hmVlJ7kSq8+V+6JQDlpmV5Gzd5cz94IBlZiW5Albu3A850nyNSHpIUnI2VzOrl4xzumfN/ZCjhXUVsBU4LsO6zGzAck7glzv3Q08tLEkrgLcDn89THTOrg6HLmlP4FPBh4NgMdTGzmhi6oTmSLgDGImLTPMtdLmmjpI2p97CYWbXq2sLqNZHqhZKeAm6h1an2pekLRcSNEbEyIlam3ihpZtXpNFg1KmBFxDURsSIiTgPWAN+OiPdkq5mZDUxdA5bvwzKzkqGewC8i7gHuybEuMxu8una6u4VlZlPUeQK/SgOWpMrSzqfO1pAyq0HqxYTR0dGkckuXLu26TGodU/fj+Ph412VSryLv2bMnqVyK1FOllHIpM17k4oBlZo3hgGVmjeGAZWaNkHMsYW4OWGZW4haWmTWGA5aZNYYDlpk1hgOWmTVCnTvdnfnZzEoyZn5eK2lM0pYc9XLAMrOSjLM1fBFYlatePiU0s5KMmZ/vLRKoZuGAZWZTdDn4uePMzzk4YJlZSe7Mz7lUHrDqPlvDokWLui6zePHipG2lzLoAcMIJJ3Rd5rjj0rKwLVy4MKnc4cOHuy6zd29yBvOuHTp0KKncwYMHKyuXsg9T/r5mUterhG5hmdkUdZ4Py1cJzawk420NNwPfA86UtF3SZb3Uq6cWlqRRWklUzwICuDQivtfLOs1s8DJeJbwoy4oKvZ4S/hPwjYh4l6RFQFpnjpnVSl1PCZMDlqSlwBuASwAi4hCQ1pNpZrUxrENzTgd+BvyrpIckfV6SM6WaDYG65iXsJWAtAM4GboiIVwP7gaunL+RU9WbNM4wBazuwPSLuL17fSiuATeFU9WbNM3QBKyKeAZ6WdGbx1rnAY1lqZWYDVdeA1etVwj8D1hVXCJ8E3td7lcxskOp842hPASsiNgOVjSMys2rU9Sqhh+aYWclQtrBSVDX4eWRkpOsykDbYNyW9PcAVV1yRVG5sbKzrMrt3707aVuog4ZRB5KOjo0nbuvPOO7sus2/fvqRtpZZLOR5TjvtcHLDMrBGGtg/LzIaTA5aZNYYDlpk1hq8SmlkjuA/LzBrFAcvMGqOuActTJJtZSc6xhJJWSfqBpG2SSjO6dMMtLDObIucEfpJGgM8Cb6E1w8sDkm6PiKSJEtzCMrOSjC2sc4BtEfFkMSvxLcDq1Hq5hWVmJRkzPy8Hnm57vR34rdR6OWCZWYkzP5tZY2S8SrgDOLXt9YrivSSNCFgpMzykpuyucmaI8fHxpHIpKcxTZ11ILZci5fcCWLCg+8M49TtLnUGhymO4V5lvHH0AOEPS6bQC1Rrg3akra0TAMrNq5bpKGBHjkq4E7gJGgLUR8Wjq+hywzKwk542jEbEeWJ9jXT3d1iDpLyQ9KmmLpJslHZ2jUmY2WHVNQpEcsCQtB/4cWBkRZ9Fq7q3JVTEzG4xOg1UTs+YsAI6RdBhYDPy09yqZ2aAN3VjCiNgB/D3wE2AnsCci7s5VMTMbnLq2sHo5JVxG6xb704GXAUskvWeG5Zyq3qxhJiYmOnpUrZdO9zcD/xMRP4uIw8DXgNdOX8ip6s2aZVj7sH4CvEbSYuAFWqnqN85dxMyaoK59WMkBKyLul3Qr8CAwDjwE3Dh3KTNrgqELWAARcR1wXaa6mFlNDGXAMrPhk3MCv9wcsMysxC2sHqTsvNQdnvKf5ciRI0nbWrduXVK5k046qesyy5YtS9rWwoULk8qlzLzw/PPPJ21rbGys6zKp31lqy6PKYzgHBywzawwHLDNrDAcsM2sEZ342s0bxVUIza4y6trCcl9DMSqoYSyjpD4sJQCckdZR5xwHLzKaocPDzFuD3gXs7LeBTQjMrqeKUMCK2QnfZgRywzKwkY+bnrBywzKyki6uEc2Z+lvRN4KUzfHRtRHy923o5YJnZFDnvw4qIN2dZUcEBy8xK6npbQ+UBK2VHVDkgOWXQ7gsvvJC0rdQ57vfu3ZtULkWVg59Tf6+U/Zj6naX8XpB2PA7y5s0qApakdwKfAV4C/JekzRHx1rnKuIVlZiUVXSW8DbitmzIOWGY2RZ0n8Jv3xlFJayWNSdrS9t7xkjZIeqL4mTbZkpnVUl2z5nRyp/sXgVXT3rsa+FZEnAF8q3htZkOisQErIu4Fnpv29mrgpuL5TcA7MtfLzAaorgErtQ/r5IjYWTx/Bjg5U33MrAaG9raGiAhJs/52ki4HLgcYHR3tdXNm1md1nsAvdbaGZyWdAlD8nDULgFPVmzXPxMRER4+qpQas24GLi+cXA12PCTKz+mpsH5akm4E30hqVvZ1WpuePA1+RdBnwY+CP+llJM6tWXU8J5w1YEXHRLB+dm7kuZlYDde7D8p3uZlbigGVmjVHXoTlDO1vD+Ph412UADh061HWZAwcOJG1rz549SeVS/OIXv0gqt2BB2iGSsv9TZ69I2Y+p31nK8QFp+yPluM/RMvIpoZk1igOWmTWGA5aZNYYDlpk1hgOWmTVCVRP4Sboe+D3gEPAj4H0RsXuuMs78bGYlFQ3N2QCcFRGvBH4IXDNfAQcsMyupImBFxN0RMXm/x33AivnK+JTQzEoGkPn5UuDL8y3kgGVmU3TZeuo587Oka4FxYN18G3PAMrOSqjI/S7oEuAA4NzrYqAOWmZVUdJVwFfBh4HcioqOxUg5YZlZS0X1Y/wy8CNggCeC+iHj/XAUqDVipVxaqHPycksL8qKOqvdiaMgB33759SdsaGRlJKpeSmj01fXzKQObUgdapdaxq8HMOVQ1+johf7baMW1hmVuI73c2sMRywzKwx6jqB37ydL5LWShqTtKXtveslPS7pEUm3SXLCQbMh0eld7rVMVQ98EVg17b2uxwCZWXM0NmBFxL3Ac9Pe63oMkJk1R10DVo4+rDnHALWnql+6dGmGzZlZv9W1072nG4g6GQPkVPVmzTN0LaxuxwCZWTNUNYFfiqSAlTIGyMyao65tkE5ua7gZ+B5wpqTtki6jNQboWFpjgDZL+lyf62lmFWrsKWFEXDTD21/oQ13MrCbq2sLyne5mNoUzP7dJ6cwrpp7oSupsDSnbSh35n9qxefDgwa7LpM7WkDoTRcrvdvjw4aRtpcxekTrrQmodmzRbA7iFZWYNMlRXCc1suLmFZWaN4D4sM2uUKgKWpL8FVgMTwBhwSUT8dK4yTqRqZiUV3Yd1fUS8MiJeBdwBfGS+Am5hmVlJFZ3uEbG37eUSwGm+zKw7Xbaeesr8LOljwHuBPcDvzre8A5aZlVSV+TkirgWulXQNcCVw3Vwbc8Ays5KqMj+3WQesZ56A5U53MyupotNd0hltL1cDj89Xxi0sMyup6D6sj0s6k9ZtDT8G5sz6DA5YZjZNVRP4RcQfdFvGAcvMSnynew9Sdl7qf4iU0fipX26VszWMjIwkbStl9gpI2ydHjhxJ2lbKTAips3mklkv5rlP2YcbO8izrya0RAcvMquWAZWaNUOfBz0mp6ts++5CkkHRif6pnZoNQ1zndU1PVI+lU4DzgJ5nrZGYDNjEx0dGjakmp6gv/SCvVVz3bjmaWrK4trNS8hKuBHRHx8HxXkZyq3qxZ6tyH1XXAkrQY+Gtap4PzKkZu3wiwfPnyeu4FM5tiaAIW8ArgdGCydbUCeFDSORHxTM7KmdlgDE3AiojvAydNvpb0FLAyInZlrJeZDVBds+akpqo3syHVaYd7LTvdZ0lV3/75adlqY2a1MDSnhGY2/BywelDl+XSVA05TB/umDNBOTTlf5eDn1O85pVyV24Jq90cODlhm1hgOWGbWCFVN4JfCc7qbWUmVVwm7mUTBLSwzK6nqlLDbSRTcwjKzkgpbWF1NouAWlplNUVXm524mUZjkgGVmJVVkfqaLSRQmOWCZWUmuq4SzZX6W9BskTKLggGVmJf3udE+dRMEBy8ymGKoJ/Mxs+FUdsDqdRMEBy8xK3MIys8ao69AcVRlJJf0M+PEsH58I1GHWUtdjKtdjqrrX41ci4iW9rFjSN4r1d2JXRJTSAPZLpQFrLpI2znU/h+vherge9atH1Tw0x8wawwHLzBqjTgGro/FHFXA9pnI9pnI9Bqg2fVhmZvOpUwvLzGxOlQYsSask/UDSNklXz/D5iyR9ufj8fkmn9aEOp0r6jqTHJD0q6aoZlnmjpD2SNhePj+SuR9u2npL0/WI7G2f4XJI+XeyTRySdnXn7Z7b9npsl7ZX0wWnL9G1/SForaUzSlrb3jpe0QdITxc9ls5S9uFjmCUkX96Ee10t6vNjvt0kanaXsnN9hhnp8VNKOtv1//ixl5/z7GgrdJE3s5QGMAD8CXg4sAh4Gfm3aMlcAnyuerwG+3Id6nAKcXTw/FvjhDPV4I3BHRfvlKeDEOT4/H7gTEPAa4P4+f0fP0LqXp5L9AbwBOBvY0vbe3wFXF8+vBj4xQ7njgSeLn8uK58sy1+M8YEHx/BMz1aOT7zBDPT4K/FUH392cf1/D8KiyhXUOsC0inoyIQ8AtwOppy6wGbiqe3wqcq9Q8U7OIiJ0R8WDx/OfAVmB5zm1kthr4t2i5DxiVdEqftnUu8KOImO3m3uwi4l7guWlvtx8HNwHvmKHoW4ENEfFcRDwPbACSb2CcqR4RcXdEjBcv76M1BUpfzbI/OtHJ31fjVRmwlgNPt73eTjlQ/P8yxYGyBzihXxUqTjlfDdw/w8e/LelhSXdK+vV+1YHW1LB3S9ok6fIZPu9kv+WyBrh5ls+q2h8AJ0fEzuL5M8DJMyxT5X4BuJRWS3cm832HOVxZnJquneUUuer9MRC/tJ3ukl4MfBX4YETsnfbxg7ROi34T+Azwn32syusj4mzgbcCfSnpDH7c1K0mLgAuB/5jh4yr3xxTROt8Z6KVsSdcC48C6WRbp93d4A/AK4FXATuAfMq+/MaoMWDuAU9teryjem3EZSQuApcD/5q6IpIW0gtW6iPja9M8jYm9E7CuerwcWdpKCKEVE7Ch+jgG30Wrat+tkv+XwNuDBiHh2hjpWtj8Kz06e9hY/x2ZYppL9IukS4ALgj4vgWdLBd9iTiHg2Io5ExATwL7Osv6rjZKCqDFgPAGdIOr34b74GuH3aMrcDk1d73gV8e7aDJFXRJ/YFYGtEfHKWZV462Xcm6Rxa+6kfgXOJpGMnn9Pq5N0ybbHbgfcWVwtfA+xpO13K6SJmOR2san+0aT8OLga+PsMydwHnSVpWnCKdV7yXjaRVtDK6XBgRB2ZZppPvsNd6tPdZvnOW9Xfy99V8Vfbw07ri9UNaVzOuLd77G1oHBMDRtE5JtgH/Dby8D3V4Pa1TjEeAzcXjfOD9wPuLZa4EHqV1peU+4LV92h8vL7bxcLG9yX3SXhcBny322fdpTSObux5LaAWgpW3vVbI/aAXJncBhWv0ul9Hqt/wW8ATwTeD4YtmVwOfbyl5aHCvbgPf1oR7baPULTR4nk1ewXwasn+s7zFyPfy+++0doBaFTptdjtr+vYXv4Tncza4xf2k53M2seBywzawwHLDNrDAcsM2sMBywzawwHLDNrDAcsM2sMBywza4z/A4R2nNvCi1KYAAAAAElFTkSuQmCC\n", 105 | "text/plain": [ 106 | "
" 107 | ] 108 | }, 109 | "metadata": {}, 110 | "output_type": "display_data" 111 | }, 112 | { 113 | "data": { 114 | "image/png": "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\n", 115 | "text/plain": [ 116 | "
" 117 | ] 118 | }, 119 | "metadata": {}, 120 | "output_type": "display_data" 121 | } 122 | ], 123 | "source": [ 124 | "bar_images_short = dataset.get_bar_images(is_short=True)\n", 125 | "bar_images_long = dataset.get_bar_images(is_short=False)\n", 126 | "\n", 127 | "plt.figure()\n", 128 | "plt.imshow(bar_images_short[1].reshape([16,16]), cmap='gray')\n", 129 | "plt.colorbar()\n", 130 | "plt.show()\n", 131 | "\n", 132 | "plt.figure()\n", 133 | "plt.imshow(bar_images_long[1].reshape([16,16]), cmap='gray')\n", 134 | "plt.colorbar()\n", 135 | "plt.show()" 136 | ] 137 | }, 138 | { 139 | "cell_type": "markdown", 140 | "metadata": {}, 141 | "source": [ 142 | "## Reconstruct from level1" 143 | ] 144 | }, 145 | { 146 | "cell_type": "code", 147 | "execution_count": 6, 148 | "metadata": {}, 149 | "outputs": [ 150 | { 151 | "data": { 152 | "image/png": "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\n", 153 | "text/plain": [ 154 | "
" 155 | ] 156 | }, 157 | "metadata": {}, 158 | "output_type": "display_data" 159 | }, 160 | { 161 | "data": { 162 | "image/png": "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\n", 163 | "text/plain": [ 164 | "
" 165 | ] 166 | }, 167 | "metadata": {}, 168 | "output_type": "display_data" 169 | } 170 | ], 171 | "source": [ 172 | "patch1_long = model.reconstruct(rs_long, level=1)\n", 173 | "plt.figure()\n", 174 | "plt.imshow(patch1_long, cmap='gray')\n", 175 | "plt.colorbar()\n", 176 | "plt.show()\n", 177 | "\n", 178 | "patch1_short = model.reconstruct(rs_short, level=1)\n", 179 | "plt.figure()\n", 180 | "plt.imshow(patch1_short, cmap='gray')\n", 181 | "plt.colorbar()\n", 182 | "plt.show()" 183 | ] 184 | }, 185 | { 186 | "cell_type": "markdown", 187 | "metadata": {}, 188 | "source": [ 189 | "## Reconstruct from level2" 190 | ] 191 | }, 192 | { 193 | "cell_type": "code", 194 | "execution_count": 7, 195 | "metadata": {}, 196 | "outputs": [ 197 | { 198 | "data": { 199 | "image/png": "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\n", 200 | "text/plain": [ 201 | "
" 202 | ] 203 | }, 204 | "metadata": {}, 205 | "output_type": "display_data" 206 | }, 207 | { 208 | "data": { 209 | "image/png": "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\n", 210 | "text/plain": [ 211 | "
" 212 | ] 213 | }, 214 | "metadata": {}, 215 | "output_type": "display_data" 216 | } 217 | ], 218 | "source": [ 219 | "patch2_long = model.reconstruct(rh_long, level=2)\n", 220 | "plt.figure()\n", 221 | "plt.imshow(patch2_long, cmap='gray')\n", 222 | "plt.colorbar()\n", 223 | "plt.show()\n", 224 | "\n", 225 | "patch2_short = model.reconstruct(rh_short, level=2)\n", 226 | "plt.figure()\n", 227 | "plt.imshow(patch2_short, cmap='gray')\n", 228 | "plt.colorbar()\n", 229 | "plt.show()" 230 | ] 231 | }, 232 | { 233 | "cell_type": "code", 234 | "execution_count": null, 235 | "metadata": {}, 236 | "outputs": [], 237 | "source": [] 238 | } 239 | ], 240 | "metadata": { 241 | "kernelspec": { 242 | "display_name": "Python 3", 243 | "language": "python", 244 | "name": "python3" 245 | }, 246 | "language_info": { 247 | "codemirror_mode": { 248 | "name": "ipython", 249 | "version": 3 250 | }, 251 | "file_extension": ".py", 252 | "mimetype": "text/x-python", 253 | "name": "python", 254 | "nbconvert_exporter": "python", 255 | "pygments_lexer": "ipython3", 256 | "version": "3.6.5" 257 | } 258 | }, 259 | "nbformat": 4, 260 | "nbformat_minor": 2 261 | } 262 | -------------------------------------------------------------------------------- /main.py: -------------------------------------------------------------------------------- 1 | # -*- coding: utf-8 -*- 2 | import numpy as np 3 | import os 4 | import cv2 5 | import imageio 6 | 7 | from dataset import Dataset 8 | from model import Model 9 | 10 | def main(): 11 | dataset = Dataset(scale=1.0, shuffle=False) 12 | model = Model() 13 | model.train(dataset) 14 | 15 | model.save("saved") 16 | 17 | if not os.path.exists("result"): 18 | os.mkdir("result") 19 | 20 | for i in range(32): 21 | u1 = model.Us[1][:,i].reshape(16,16) 22 | u1 = cv2.resize(u1, None, fx=4, fy=4, interpolation=cv2.INTER_NEAREST) 23 | imageio.imwrite("result/u1_{:0>2}.png".format(i), u1) 24 | 25 | for i in range(128): 26 | u2 = model.get_level2_rf(i) 27 | u2 = cv2.resize(u2, None, fx=4, fy=4, interpolation=cv2.INTER_NEAREST) 28 | imageio.imwrite("result/u2_{:0>3}.png".format(i), u2) 29 | 30 | 31 | if __name__ == '__main__': 32 | main() 33 | -------------------------------------------------------------------------------- /model.py: -------------------------------------------------------------------------------- 1 | # -*- coding: utf-8 -*- 2 | import numpy as np 3 | import os 4 | 5 | 6 | class Model: 7 | def __init__(self, iteration=30): 8 | self.iteration = iteration 9 | 10 | self.k1 = 0.0005 # Learning rate for r 11 | self.k2_init = 0.005 # Initial learning rate for U 12 | 13 | self.sigma_sq = 1.0 # Variance of observation distribution of I 14 | self.sigma_sq_td = 10.0 # Variance of observation distribution of r 15 | self.alpha1 = 1.0 # Precision param of r prior (var=1.0, std=1.0) 16 | self.alpha2 = 0.05 # Precision param of r_td prior (var=20.0, std=4.5) 17 | self.lambd1 = 0.02 # Precision param of U prior (var=50.0, std=7.1) 18 | self.lambd2 = 0.00001 # Precision param of Uh prior 19 | 20 | U_scale = 7.0 21 | self.Us = (np.random.rand(3,256,32) - 0.5) * U_scale 22 | self.Uh = (np.random.rand(96,128) - 0.5) * U_scale 23 | 24 | self.k2 = self.k2_init 25 | 26 | # Scaling parameter for learning rate of level2 27 | self.level2_lr_scale = 10.0 28 | 29 | def apply_images(self, images, training): 30 | rs = np.zeros([96], dtype=np.float32) 31 | rh = np.zeros([128], dtype=np.float32) 32 | 33 | error_tds = np.zeros([96], dtype=np.float32) 34 | 35 | for i in range(self.iteration): 36 | # Loop for iterations 37 | 38 | # Calculate r_td 39 | r_tds = self.Uh.dot(rh) # (96,) 40 | 41 | for j in range(3): 42 | I = images[j] 43 | r = rs[ 32*j:32*(j+1)] 44 | r_td = r_tds[32*j:32*(j+1)] 45 | 46 | U = self.Us[j] 47 | Ur = U.dot(r) 48 | 49 | error = I - Ur 50 | error_td = r_td - r 51 | 52 | dr = (self.k1/self.sigma_sq) * U.T.dot(error) + \ 53 | (self.k1/self.sigma_sq_td) * error_td - self.k1 * self.alpha1 * r 54 | if training: 55 | dU = (self.k2/self.sigma_sq) * np.outer(error, r) \ 56 | - self.k2 * self.lambd1 * U 57 | self.Us[j] += dU 58 | rs[32*j:32*(j+1)] += dr 59 | 60 | error_tds[32*j:32*(j+1)] = error_td 61 | 62 | # Level2 update 63 | drh = (self.k1*self.level2_lr_scale / self.sigma_sq_td) * self.Uh.T.dot(-error_tds) \ 64 | - self.k1*self.level2_lr_scale * self.alpha2 * rh 65 | if training: 66 | dUh = (self.k2*self.level2_lr_scale / self.sigma_sq_td) * np.outer(-error_tds, rh) \ 67 | - self.k2*self.level2_lr_scale * self.lambd2 * self.Uh 68 | # (96,128) 69 | self.Uh += dUh 70 | rh += drh 71 | 72 | return rs, r_tds, rh, error_tds 73 | 74 | def train(self, dataset): 75 | self.k2 = self.k2_init 76 | 77 | patch_size = len(dataset.patches) # 2375 78 | 79 | for i in range(patch_size): 80 | # Loop for all patches 81 | images = dataset.get_images(i) 82 | rs, r_tds, rh, error_tds = self.apply_images(images, training=True) 83 | 84 | if i % 100 == 0: 85 | print("rs std={:.2f}".format(np.std(rs))) 86 | print("r_tds std={:.2f}".format(np.std(r_tds))) 87 | print("U std={:.2f}".format(np.std(self.Us))) 88 | print("Uh std={:.2f}".format(np.std(self.Uh))) 89 | 90 | if i % 40 == 0: 91 | # Decay learning rate for U 92 | self.k2 = self.k2 / 1.015 93 | 94 | print("train finished") 95 | 96 | def reconstruct(self, r, level=1): 97 | if level==1: 98 | rs = r 99 | else: 100 | rh = r 101 | rs = self.Uh.dot(rh) # (96,) 102 | 103 | patch = np.zeros((16,26), dtype=np.float32) 104 | 105 | for i in range(3): 106 | r = rs[32*i:32*(i+1)] 107 | U = self.Us[i] 108 | Ur = U.dot(r).reshape(16,16) 109 | patch[:, 5*i:5*i+16] += Ur 110 | return patch 111 | 112 | def get_level2_rf(self, index): 113 | Uh0 = self.Uh[:,index][0:32] 114 | Uh1 = self.Uh[:,index][32:64] 115 | Uh2 = self.Uh[:,index][64:96] 116 | 117 | UU0 = self.Us[0].dot(Uh0).reshape((16,16)) 118 | UU1 = self.Us[1].dot(Uh1).reshape((16,16)) 119 | UU2 = self.Us[2].dot(Uh2).reshape((16,16)) 120 | 121 | rf = np.zeros((16,26), dtype=np.float32) 122 | rf[:, 5*0:5*0+16] += UU0 123 | rf[:, 5*1:5*1+16] += UU1 124 | rf[:, 5*2:5*2+16] += UU2 125 | return rf 126 | 127 | def save(self, dir_name): 128 | if not os.path.exists(dir_name): 129 | os.makedirs(dir_name) 130 | file_path = os.path.join(dir_name, "model") 131 | 132 | np.savez_compressed(file_path, 133 | Us=self.Us, 134 | Uh=self.Uh) 135 | print("saved: {}".format(dir_name)) 136 | 137 | def load(self, dir_name): 138 | file_path = os.path.join(dir_name, "model.npz") 139 | if not os.path.exists(file_path): 140 | print("saved file not found") 141 | return 142 | data = np.load(file_path) 143 | self.Us = data["Us"] 144 | self.Uh = data["Uh"] 145 | print("loaded: {}".format(dir_name)) 146 | -------------------------------------------------------------------------------- /model_test.py: -------------------------------------------------------------------------------- 1 | # -*- coding: utf-8 -*- 2 | import numpy as np 3 | import unittest 4 | 5 | from dataset import Dataset 6 | from model import Model 7 | 8 | DEBUG_TEST_SAVING = False 9 | 10 | 11 | class ModeTest(unittest.TestCase): 12 | def test_init(self): 13 | dataset = Dataset(scale=1.0) 14 | model = Model(iteration=1) 15 | model.train(dataset) 16 | 17 | images = dataset.get_images(0) 18 | rs, r_tds, rh, error_tds = model.apply_images(images, training=True) 19 | self.assertEqual(rs.shape, (96,)) 20 | self.assertEqual(r_tds.shape, (96,)) 21 | self.assertEqual(rh.shape, (128,)) 22 | self.assertEqual(error_tds.shape, (96,)) 23 | 24 | patch_rec1 = model.reconstruct(rs, level=1) 25 | self.assertEqual(patch_rec1.shape, (16, 26)) 26 | 27 | patch_rec2 = model.reconstruct(rh, level=2) 28 | self.assertEqual(patch_rec2.shape, (16, 26)) 29 | 30 | bar_images_short = dataset.get_bar_images(is_short=True) 31 | rs, r_tds, rh, error_tds = model.apply_images(bar_images_short, training=False) 32 | self.assertEqual(rs.shape, (96,)) 33 | self.assertEqual(r_tds.shape, (96,)) 34 | self.assertEqual(rh.shape, (128,)) 35 | self.assertEqual(error_tds.shape, (96,)) 36 | 37 | bar_images_long = dataset.get_bar_images(is_short=False) 38 | rs, r_tds, rh, error_tds = model.apply_images(bar_images_long, training=False) 39 | self.assertEqual(rs.shape, (96,)) 40 | self.assertEqual(r_tds.shape, (96,)) 41 | self.assertEqual(rh.shape, (128,)) 42 | self.assertEqual(error_tds.shape, (96,)) 43 | 44 | def test_save(self): 45 | if DEBUG_TEST_SAVING: 46 | model = Model(iteration=1) 47 | model.save("tmp") 48 | model.load("tmp") 49 | 50 | 51 | 52 | if __name__ == '__main__': 53 | unittest.main() 54 | --------------------------------------------------------------------------------