| 104 | |
| 105 | |
| 106 | class CNN(object): |
| 107 | def __init__(self, convpool_layer_sizes, hidden_layer_sizes): |
| 108 | self.convpool_layer_sizes = convpool_layer_sizes |
| 109 | self.hidden_layer_sizes = hidden_layer_sizes |
| 110 | |
| 111 | def fit(self, X, Y, lr=1e-4, mu=0.99, reg=1e-6, decay=0.99999, eps=1e-2, batch_sz=30, epochs=100, show_fig=True): |
| 112 | lr = np.float32(lr) |
| 113 | mu = np.float32(mu) |
| 114 | reg = np.float32(reg) |
| 115 | decay = np.float32(decay) |
| 116 | eps = np.float32(eps) |
| 117 | |
| 118 | # make a validation set |
| 119 | X, Y = shuffle(X, Y) |
| 120 | X = X.astype(np.float32) |
| 121 | Y = Y.astype(np.int32) |
| 122 | Xvalid, Yvalid = X[-1000:], Y[-1000:] |
| 123 | X, Y = X[:-1000], Y[:-1000] |
| 124 | |
| 125 | # initialize convpool layers |
| 126 | N, c, width, height = X.shape |
| 127 | mi = c |
| 128 | outw = width |
| 129 | outh = height |
| 130 | self.convpool_layers = [] |
| 131 | for mo, fw, fh in self.convpool_layer_sizes: |
| 132 | layer = ConvPoolLayer(mi, mo, fw, fh) |
| 133 | self.convpool_layers.append(layer) |
| 134 | outw = (outw - fw + 1) / 2 |
| 135 | outh = (outh - fh + 1) / 2 |
| 136 | mi = mo |
| 137 | |
| 138 | # initialize mlp layers |
| 139 | K = len(set(Y)) |
| 140 | self.hidden_layers = [] |
| 141 | M1 = self.convpool_layer_sizes[-1][0]*outw*outh # size must be same as output of last convpool layer |
| 142 | count = 0 |
| 143 | for M2 in self.hidden_layer_sizes: |
| 144 | h = HiddenLayer(M1, M2, count) |
| 145 | self.hidden_layers.append(h) |
| 146 | M1 = M2 |
| 147 | count += 1 |
| 148 | |
| 149 | # logistic regression layer |
| 150 | W, b = init_weight_and_bias(M1, K) |
| 151 | self.W = theano.shared(W, 'W_logreg') |
| 152 | self.b = theano.shared(b, 'b_logreg') |
| 153 | |
| 154 | # collect params for later use |
| 155 | self.params = [self.W, self.b] |
| 156 | for c in self.convpool_layers: |
| 157 | self.params += c.params |
| 158 | for h in self.hidden_layers: |
| 159 | self.params += h.params |
| 160 | |
| 161 | # for momentum |
| 162 | dparams = [theano.shared(np.zeros(p.get_value().shape, dtype=np.float32)) for p in self.params] |
| 163 | |