Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
Download

📚 The CoCalc Library - books, templates and other resources

132937 views
License: OTHER
1
""" Load VGGNet weights needed for the implementation of the paper
2
"A Neural Algorithm of Artistic Style" by Gatys et al. in TensorFlow.
3
4
Author: Chip Huyen ([email protected])
5
Prepared for the class CS 20SI: "TensorFlow for Deep Learning Research"
6
For more details, please read the assignment handout:
7
http://web.stanford.edu/class/cs20si/assignments/a2.pdf
8
"""
9
10
import numpy as np
11
import tensorflow as tf
12
import scipy.io
13
14
def _weights(vgg_layers, layer, expected_layer_name):
15
""" Return the weights and biases already trained by VGG
16
"""
17
W = vgg_layers[0][layer][0][0][2][0][0]
18
b = vgg_layers[0][layer][0][0][2][0][1]
19
layer_name = vgg_layers[0][layer][0][0][0][0]
20
assert layer_name == expected_layer_name
21
return W, b.reshape(b.size)
22
23
def _conv2d_relu(vgg_layers, prev_layer, layer, layer_name):
24
""" Return the Conv2D layer with RELU using the weights, biases from the VGG
25
model at 'layer'.
26
Inputs:
27
vgg_layers: holding all the layers of VGGNet
28
prev_layer: the output tensor from the previous layer
29
layer: the index to current layer in vgg_layers
30
layer_name: the string that is the name of the current layer.
31
It's used to specify variable_scope.
32
33
Output:
34
relu applied on the convolution.
35
36
Note that you first need to obtain W and b from vgg-layers using the function
37
_weights() defined above.
38
W and b returned from _weights() are numpy arrays, so you have
39
to convert them to TF tensors using tf.constant.
40
Note that you'll have to do apply relu on the convolution.
41
Hint for choosing strides size:
42
for small images, you probably don't want to skip any pixel
43
"""
44
with tf.variable_scope(layer_name) as scope:
45
W, b = _weights(vgg_layers, layer, layer_name)
46
W = tf.constant(W, name='weights')
47
b = tf.constant(b, name='bias')
48
conv2d = tf.nn.conv2d(prev_layer, filter=W, strides=[1, 1, 1, 1], padding='SAME')
49
return tf.nn.relu(conv2d + b)
50
51
def _avgpool(prev_layer):
52
""" Return the average pooling layer. The paper suggests that average pooling
53
actually works better than max pooling.
54
Input:
55
prev_layer: the output tensor from the previous layer
56
57
Output:
58
the output of the tf.nn.avg_pool() function.
59
Hint for choosing strides and kszie: choose what you feel appropriate
60
"""
61
return tf.nn.avg_pool(prev_layer, ksize=[1, 2, 2, 1], strides=[1, 2, 2, 1],
62
padding='SAME', name='avg_pool_')
63
64
def load_vgg(path, input_image):
65
""" Load VGG into a TensorFlow model.
66
Use a dictionary to hold the model instead of using a Python class
67
"""
68
vgg = scipy.io.loadmat(path)
69
vgg_layers = vgg['layers']
70
71
graph = {}
72
graph['conv1_1'] = _conv2d_relu(vgg_layers, input_image, 0, 'conv1_1')
73
graph['conv1_2'] = _conv2d_relu(vgg_layers, graph['conv1_1'], 2, 'conv1_2')
74
graph['avgpool1'] = _avgpool(graph['conv1_2'])
75
graph['conv2_1'] = _conv2d_relu(vgg_layers, graph['avgpool1'], 5, 'conv2_1')
76
graph['conv2_2'] = _conv2d_relu(vgg_layers, graph['conv2_1'], 7, 'conv2_2')
77
graph['avgpool2'] = _avgpool(graph['conv2_2'])
78
graph['conv3_1'] = _conv2d_relu(vgg_layers, graph['avgpool2'], 10, 'conv3_1')
79
graph['conv3_2'] = _conv2d_relu(vgg_layers, graph['conv3_1'], 12, 'conv3_2')
80
graph['conv3_3'] = _conv2d_relu(vgg_layers, graph['conv3_2'], 14, 'conv3_3')
81
graph['conv3_4'] = _conv2d_relu(vgg_layers, graph['conv3_3'], 16, 'conv3_4')
82
graph['avgpool3'] = _avgpool(graph['conv3_4'])
83
graph['conv4_1'] = _conv2d_relu(vgg_layers, graph['avgpool3'], 19, 'conv4_1')
84
graph['conv4_2'] = _conv2d_relu(vgg_layers, graph['conv4_1'], 21, 'conv4_2')
85
graph['conv4_3'] = _conv2d_relu(vgg_layers, graph['conv4_2'], 23, 'conv4_3')
86
graph['conv4_4'] = _conv2d_relu(vgg_layers, graph['conv4_3'], 25, 'conv4_4')
87
graph['avgpool4'] = _avgpool(graph['conv4_4'])
88
graph['conv5_1'] = _conv2d_relu(vgg_layers, graph['avgpool4'], 28, 'conv5_1')
89
graph['conv5_2'] = _conv2d_relu(vgg_layers, graph['conv5_1'], 30, 'conv5_2')
90
graph['conv5_3'] = _conv2d_relu(vgg_layers, graph['conv5_2'], 32, 'conv5_3')
91
graph['conv5_4'] = _conv2d_relu(vgg_layers, graph['conv5_3'], 34, 'conv5_4')
92
graph['avgpool5'] = _avgpool(graph['conv5_4'])
93
94
return graph
95