|
import tensorflow as tf |
|
import tensorflow.contrib as tfc |
|
import numpy as np |
|
|
|
|
|
class CNN_BN(object): |
|
|
|
def __init__(self, Xshape, K, optimizer = None): |
|
|
|
self.X = tf.placeholder(tf.float32, shape = [None] + Xshape) |
|
self.Xshape = Xshape |
|
self.params = dict() |
|
|
|
### definition of the network |
|
BN_offset = None |
|
BN_scale = None |
|
BN_eps = 0.001 |
|
|
|
### conv1 |
|
# |
|
Wshape = [5, 5, 1, 32] |
|
with tf.variable_scope('conv1'): |
|
W = tf.get_variable('W', shape = Wshape, initializer = tfc.layers.xavier_initializer_conv2d()) |
|
mean = tf.get_variable('mean', shape = Wshape[-1], initializer = tf.zeros_initializer) |
|
var = tf.get_variable('var', shape = Wshape[-1], initializer = tf.ones_initializer) |
|
|
|
WX = tf.nn.conv2d(self.X, W, [1, 2, 2, 1], padding = 'SAME') |
|
Y = tf.nn.batch_normalization(WX, mean, var, BN_offset, BN_scale, BN_eps) |
|
conv1 = tf.nn.relu(Y) |
|
self.params[W.name] = W |
|
self.params[mean.name] = mean |
|
self.params[var.name] = var |
|
|
|
### pool1 |
|
# |
|
Wshape = [1, 2, 2, 1] |
|
pool1 = tf.nn.max_pool(conv1, Wshape, [1, 2, 2, 1], padding = 'SAME') |
|
|
|
### conv2 |
|
# |
|
Wshape = [5, 5, 32, 64] |
|
with tf.variable_scope('conv2'): |
|
W = tf.get_variable('W', shape = Wshape, initializer = tfc.layers.xavier_initializer_conv2d()) |
|
mean = tf.get_variable('mean', shape = Wshape[-1], initializer = tf.zeros_initializer) |
|
var = tf.get_variable('var', shape = Wshape[-1], initializer = tf.ones_initializer) |
|
|
|
WX = tf.nn.conv2d(pool1, W, [1, 2, 2, 1], padding = 'SAME') |
|
Y = tf.nn.batch_normalization(WX, mean, var, BN_offset, BN_scale, BN_eps) |
|
conv2 = tf.nn.relu(Y) |
|
self.params[W.name] = W |
|
self.params[mean.name] = mean |
|
self.params[var.name] = var |
|
|
|
### pool2 |
|
# |
|
Wshape = [1, 2, 2, 1] |
|
pool2 = tf.nn.max_pool(conv2, Wshape, [1, 2, 2, 1], padding = 'SAME') |
|
|
|
### fc |
|
# |
|
pool2_flat = tfc.layers.flatten(pool2) |
|
Wshape = [pool2_flat.shape[1], 1024] |
|
with tf.variable_scope('fc'): |
|
W = tf.get_variable('W', shape = Wshape, initializer = tfc.layers.xavier_initializer()) |
|
mean = tf.get_variable('mean', shape = Wshape[-1], initializer = tf.zeros_initializer) |
|
var = tf.get_variable('var', shape = Wshape[-1], initializer = tf.ones_initializer) |
|
|
|
WX = tf.matmul(pool2_flat, W) |
|
Y = tf.nn.batch_normalization(WX, mean, var, BN_offset, BN_scale, BN_eps) |
|
fc = tf.nn.relu(Y) |
|
self.params[W.name] = W |
|
self.params[mean.name] = mean |
|
self.params[var.name] = var |
|
|
|
### logit |
|
# |
|
Wshape = [1024, K] |
|
with tf.variable_scope('logit'): |
|
W = tf.get_variable('W', shape = Wshape, initializer = tfc.layers.xavier_initializer()) |
|
b = tf.get_variable('b', shape = Wshape[-1], initializer = tf.zeros_initializer) |
|
|
|
logit = tf.matmul(fc, W) + b |
|
self.params[W.name] = W |
|
self.params[b.name] = b |
|
|
|
### softmax |
|
# |
|
self.Y = logit |
|
self.Z = tf.nn.softmax(logit) |
|
|
|
|
|
### definition for output computation |
|
# |
|
self.cg_output = self.Z |
|
|
|
### definition for cost |
|
# |
|
self.label = tf.placeholder(tf.int64, shape = [None]) |
|
cross_entropy = tf.nn.sparse_softmax_cross_entropy_with_logits(labels = self.label, logits = self.Y) |
|
cost = tf.reduce_mean(cross_entropy) |
|
correct_prediction = tf.equal(tf.argmax(self.Y, 1), self.label) |
|
accuracy = tf.reduce_mean(tf.cast(correct_prediction, tf.float32)) |
|
#self.cg_test = (cost, accuracy) |
|
self.cg_test = (cross_entropy, correct_prediction) |
|
|
|
### definition for training |
|
# |
|
self.optimizer = optimizer |
|
if optimizer != None: |
|
self.cg_train = self.optimizer.minimize(cost) |
|
|
|
### definition for parameter initialization |
|
# |
|
self.cg_init = tf.global_variables_initializer() |
|
|
|
### starting the session |
|
# |
|
self.sess = tf.InteractiveSession() |
|
|
|
|
|
def init(self): |
|
|
|
rv = self.sess.run(self.cg_init) |
|
return rv |
|
|
|
|
|
def output(self, X): |
|
|
|
d = {self.X: X} |
|
rv = self.sess.run(self.cg_output, feed_dict = d) |
|
return rv |
|
|
|
|
|
def train(self, X, lab): |
|
|
|
d = {self.X: X, self.label: lab} |
|
rv = self.sess.run(self.cg_train, feed_dict = d) |
|
return rv |
|
|
|
|
|
def test(self, X, lab): |
|
|
|
d = {self.X: X, self.label: lab} |
|
rv = self.sess.run(self.cg_test, feed_dict = d) |
|
return rv |
|
|
|
|
|
def getWeight(self): |
|
|
|
return self.sess.run(self.params) |
|
|
|
|
|
def setWeight(self, vals_dict): |
|
|
|
L = [] |
|
for k in vals_dict.keys(): |
|
L.append(tf.assign(self.params[k], vals_dict[k])) |
|
self.sess.run(L) |
|
|
|
|
|
if __name__ == '__main__': |
|
|
|
with tf.Graph().as_default(): |
|
cnn = CNN_BN([28, 28, 1], 10) |
|
|
|
cnn.init() |