提交 d5944c96 authored 作者: nke001's avatar nke001 提交者: abergeron

Ccw4057 (#4592)

* flake 8 changes * flake 8 changes * add missing imports * code cleanup * code clean up * flake 8 changes * code cleanup * code cleanup * code cleanup * code cleanup * add missing import
上级 74b4c807
from __future__ import absolute_import, print_function, division
from __future__ import absolute_import, print_function, division from __future__ import absolute_import, print_function, division
import sys, time, unittest import time
import numpy
import numpy as N import numpy as N
from six.moves import xrange from six.moves import xrange
from theano.tests import unittest_tools as utt
from theano import function, Mode from theano import function, Mode
import theano.tensor as T import theano.tensor as T
...@@ -38,7 +36,6 @@ def flip(kern, kshp): ...@@ -38,7 +36,6 @@ def flip(kern, kshp):
flip[k, m, i, j] = next(it) flip[k, m, i, j] = next(it)
else: else:
raise NotImplementedError() raise NotImplementedError()
return flip return flip
global_rng = N.random.RandomState(3423489) global_rng = N.random.RandomState(3423489)
...@@ -46,7 +43,8 @@ global_rng = N.random.RandomState(3423489) ...@@ -46,7 +43,8 @@ global_rng = N.random.RandomState(3423489)
dmatrix4 = T.TensorType('float64', (False, False, False, False)) dmatrix4 = T.TensorType('float64', (False, False, False, False))
def exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp, kshps, nkerns, def exec_multilayer_conv_nnet_old(
conv_mode, ss, bsize, imshp, kshps, nkerns,
unroll_batch=0, unroll_kern=0, img=T.dmatrix(), validate=True, unroll_batch=0, unroll_kern=0, img=T.dmatrix(), validate=True,
conv_op_py=False, do_print=True, repeat=1, conv_op_py=False, do_print=True, repeat=1,
unroll_patch=False, unroll_patch_size=False, verbose=0): unroll_patch=False, unroll_patch_size=False, verbose=0):
...@@ -68,7 +66,6 @@ def exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp, kshps, nkerns, ...@@ -68,7 +66,6 @@ def exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp, kshps, nkerns,
xrange(len(nkerns))): xrange(len(nkerns))):
if do_print: if do_print:
print('************* layer %i ***************' % n_layer) print('************* layer %i ***************' % n_layer)
print(conv_mode, ss, n_layer, kshp, nkern) print(conv_mode, ss, n_layer, kshp, nkern)
# actual values # actual values
...@@ -79,10 +76,11 @@ def exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp, kshps, nkerns, ...@@ -79,10 +76,11 @@ def exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp, kshps, nkerns,
# check first stage # check first stage
padimg = imgval padimg = imgval
if conv_mode == 'full': if conv_mode == 'full':
padimg_shp = N.array(imshp[1:]) + 2*(N.array(kshp) - N.array([1, 1])) padimg_shp = N.array(imshp[1:]) + 2 * (N.array(kshp) - N.array([1, 1]))
padimg = N.zeros(N.r_[bsize, imshp[0], padimg_shp]) padimg = N.zeros(N.r_[bsize, imshp[0], padimg_shp])
padimg[:, :, kshp[0]-1:-kshp[0]+1, padimg[
kshp[1]-1:-kshp[1]+1] = imgval :, :, kshp[0] - 1:-kshp[0] + 1,
kshp[1] - 1:-kshp[1] + 1] = imgval
outshp = N.hstack((nkern, ConvOp.getOutputShape(imshp[1:], kshp, ss, conv_mode))) outshp = N.hstack((nkern, ConvOp.getOutputShape(imshp[1:], kshp, ss, conv_mode)))
...@@ -97,7 +95,7 @@ def exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp, kshps, nkerns, ...@@ -97,7 +95,7 @@ def exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp, kshps, nkerns,
for b in xrange(bsize): # loop over batches for b in xrange(bsize): # loop over batches
for n in xrange(nkern): # loop over filters for n in xrange(nkern): # loop over filters
for i in xrange(imshp[0]): # loop over input feature maps for i in xrange(imshp[0]): # loop over input feature maps
outval[b, n, ...] += _convolve2d(\ outval[b, n, ...] += _convolve2d(
imgval[b, i, ...], w_flip[n, i, ...], 1, val, bval, 0)[0::ss[0], 0::ss[1]] imgval[b, i, ...], w_flip[n, i, ...], 1, val, bval, 0)[0::ss[0], 0::ss[1]]
ntot += time.time() - time1 ntot += time.time() - time1
...@@ -108,8 +106,8 @@ def exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp, kshps, nkerns, ...@@ -108,8 +106,8 @@ def exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp, kshps, nkerns,
else: else:
conv_op = ConvOp(imshp, kshp, nkern, bsize, ss[0], ss[1], conv_mode, conv_op = ConvOp(imshp, kshp, nkern, bsize, ss[0], ss[1], conv_mode,
unroll_batch=unroll_batch, unroll_kern=unroll_kern, unroll_patch=unroll_patch, verbose=verbose)(inputs4, kerns4) unroll_batch=unroll_batch, unroll_kern=unroll_kern, unroll_patch=unroll_patch, verbose=verbose)(inputs4, kerns4)
l1shp = N.hstack((nkern, # l1shp = N.hstack((nkern,
ConvOp.getOutputShape(imshp[1:], kshp, ss, conv_mode))) # ConvOp.getOutputShape(imshp[1:], kshp, ss, conv_mode)))
propup2 = function([inputs4, kerns4], conv_op) propup2 = function([inputs4, kerns4], conv_op)
propup3 = function([inputs4, kerns4], conv_op, mode=Mode(linker="py")) propup3 = function([inputs4, kerns4], conv_op, mode=Mode(linker="py"))
...@@ -125,7 +123,7 @@ def exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp, kshps, nkerns, ...@@ -125,7 +123,7 @@ def exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp, kshps, nkerns,
hidval3_ = propup3(imgval, w_flip) hidval3_ = propup3(imgval, w_flip)
hidval3 = hidval3_ # [:,:,0::ss[0],0::ss[1]] hidval3 = hidval3_ # [:,:,0::ss[0],0::ss[1]]
tpytot += time.time() - time1 tpytot += time.time() - time1
assert (N.abs(hidval2-hidval3) < 1e-5).all() assert (N.abs(hidval2 - hidval3) < 1e-5).all()
else: else:
tpytot += 0 tpytot += 0
...@@ -142,10 +140,11 @@ def exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp, kshps, nkerns, ...@@ -142,10 +140,11 @@ def exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp, kshps, nkerns,
return tctot, tpytot, ntot return tctot, tpytot, ntot
def exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp, kshps, nkerns, def exec_multilayer_conv_nnet(
conv_mode, ss, bsize, imshp, kshps, nkerns,
unroll_batch=0, unroll_kern=0, img=T.dmatrix(), unroll_batch=0, unroll_kern=0, img=T.dmatrix(),
do_print=True, repeat=1, do_print=True, repeat=1, unroll_patch=False,
unroll_patch=False, unroll_patch_size=False, verbose=0): unroll_patch_size=False, verbose=0):
# build actual input images # build actual input images
imgval = global_rng.rand(bsize, imshp[0], imshp[1], imshp[2]) imgval = global_rng.rand(bsize, imshp[0], imshp[1], imshp[2])
...@@ -163,7 +162,6 @@ def exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp, kshps, nkerns, ...@@ -163,7 +162,6 @@ def exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp, kshps, nkerns,
for kshp, kern, nkern, n_layer in zip(kshps, kerns, nkerns, xrange(len(nkerns))): for kshp, kern, nkern, n_layer in zip(kshps, kerns, nkerns, xrange(len(nkerns))):
if do_print: if do_print:
print('************* layer %i ***************' % n_layer) print('************* layer %i ***************' % n_layer)
print(conv_mode, ss, n_layer, kshp, nkern) print(conv_mode, ss, n_layer, kshp, nkern)
# actual values # actual values
...@@ -173,7 +171,7 @@ def exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp, kshps, nkerns, ...@@ -173,7 +171,7 @@ def exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp, kshps, nkerns,
outshp = N.hstack((nkern, ConvOp.getOutputShape(imshp[1:], kshp, ss, conv_mode))) outshp = N.hstack((nkern, ConvOp.getOutputShape(imshp[1:], kshp, ss, conv_mode)))
time1 = time.time() time1 = time.time()
outval = N.zeros(N.r_[bsize, outshp]) # outval = N.zeros(N.r_[bsize, outshp])
# ConvOp # ConvOp
if unroll_patch and not unroll_patch_size: if unroll_patch and not unroll_patch_size:
...@@ -182,18 +180,17 @@ def exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp, kshps, nkerns, ...@@ -182,18 +180,17 @@ def exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp, kshps, nkerns,
else: else:
conv_op = ConvOp(imshp, kshp, nkern, bsize, ss[0], ss[1], conv_mode, conv_op = ConvOp(imshp, kshp, nkern, bsize, ss[0], ss[1], conv_mode,
unroll_batch=unroll_batch, unroll_kern=unroll_kern, unroll_patch=unroll_patch, verbose=verbose)(inputs4, kerns4) unroll_batch=unroll_batch, unroll_kern=unroll_kern, unroll_patch=unroll_patch, verbose=verbose)(inputs4, kerns4)
l1shp = N.hstack((nkern, # l1shp = N.hstack((nkern,
ConvOp.getOutputShape(imshp[1:], kshp, ss, conv_mode))) # ConvOp.getOutputShape(imshp[1:], kshp, ss, conv_mode)))
propup2 = function([inputs4, kerns4], conv_op) propup2 = function([inputs4, kerns4], conv_op)
time1 = time.time() time1 = time.time()
for i in xrange(repeat): for i in xrange(repeat):
hidval2_ = propup2(imgval, w_flip) propup2(imgval, w_flip)
hidval2 = hidval2_ # [:,:,0::ss[0],0::ss[1]]
tctot += time.time() - time1 tctot += time.time() - time1
imshp = tuple(outshp) imshp = tuple(outshp)
imgval = outval.reshape(bsize, outshp[0], outshp[1], outshp[2]) # imgval = outval.reshape(bsize, outshp[0], outshp[1], outshp[2])
return tctot, tpytot, ntot return tctot, tpytot, ntot
...@@ -201,31 +198,28 @@ def exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp, kshps, nkerns, ...@@ -201,31 +198,28 @@ def exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp, kshps, nkerns,
def speed_multilayer_conv(): def speed_multilayer_conv():
# calculate the speed up of different combination of unroll # calculate the speed up of different combination of unroll
# put the paramter to the same you will try. # put the paramter to the same you will try.
# validate = False # we don't validate the result to have it much faster!
validate = False # we don't validate the result to have it much faster!
repeat = 3 repeat = 3
verbose = 1 verbose = 1
unroll_batch = [1, 2, 3, 4, 5, 6, 10] # 15, 30, 60 always much slower unroll_batch = [1, 2, 3, 4, 5, 6, 10] # 15, 30, 60 always much slower
unroll_kern = [1, 2, 3, 4, 5, 6, 10] # 15, 30, 60 always much slower unroll_kern = [1, 2, 3, 4, 5, 6, 10] # 15, 30, 60 always much slower
#unroll_batch = [1,4,5] # unroll_batch = [1,4,5]
#unroll_kern = [1,4,5] # unroll_kern = [1,4,5]
#unroll_batch = [1,4] # unroll_batch = [1,4]
#unroll_kern = [1,4] # unroll_kern = [1,4]
unroll_patch = [True, False] # unroll_patch = [True, False]
bsize = 60 # batch size bsize = 60 # batch size
imshp_start = (1, 48, 48) # un square shape to test more corner case. imshp_start = (1, 48, 48) # un square shape to test more corner case.
kshps = ([11, 12],) # un square shape to test more corner case. kshps = ([11, 12],) # un square shape to test more corner case.
nkerns = [60] # per output pixel nkerns = [60] # per output pixel
ssizes = [(1, 1), ] # (1,1)]#(2,2) bugged ssizes = [(1, 1), ] # (1,1)]#(2,2) bugged
convmodes = ['valid', 'full'] convmodes = ['valid', 'full']
do_convolve2 = False # do_convolve2 = False
a = T.dmatrix() a = T.dmatrix()
kerns = [a for i in nkerns] kerns = [a for i in nkerns]
assert len(kshps) == len(nkerns) == len(kerns) assert len(kshps) == len(nkerns) == len(kerns)
timing = N.zeros((len(unroll_batch), len(unroll_kern), 3, len(convmodes) * len(ssizes)))
timing = N.zeros((len(unroll_batch), len(unroll_kern), 3, len(convmodes)*len(ssizes)))
t_b_k = [] t_b_k = []
# calculate the timing with unrolling # calculate the timing with unrolling
...@@ -235,12 +229,12 @@ def speed_multilayer_conv(): ...@@ -235,12 +229,12 @@ def speed_multilayer_conv():
t_ = [] t_ = []
for unroll_b, n_b in zip(unroll_batch, xrange(len(unroll_batch))): for unroll_b, n_b in zip(unroll_batch, xrange(len(unroll_batch))):
for unroll_k, n_k in zip(unroll_kern, xrange(len(unroll_kern))): for unroll_k, n_k in zip(unroll_kern, xrange(len(unroll_kern))):
t_b_k.append(str(unroll_b)+"/"+str(unroll_k)) t_b_k.append(str(unroll_b) + "/" + str(unroll_k))
if not t_: if not t_:
tctot, tpytot, ntot = [], [], [] tctot, tpytot, ntot = [], [], []
for conv_mode, n_mode in zip(convmodes, xrange(len(convmodes))): for conv_mode, n_mode in zip(convmodes, xrange(len(convmodes))):
for ss, n_ss in zip(ssizes, xrange(len(ssizes))): for ss, n_ss in zip(ssizes, xrange(len(ssizes))):
# tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=unroll_b, unroll_kern=unroll_k, validate=validate, verbose=verbose,do_print=False) # tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=unroll_b, unroll_kern=unroll_k, validate=validate, verbose=verbose,do_print=False)
tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=unroll_b, unroll_kern=unroll_k, verbose=verbose, do_print=False, repeat=repeat) tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=unroll_b, unroll_kern=unroll_k, verbose=verbose, do_print=False, repeat=repeat)
tctot += [tctot_] tctot += [tctot_]
tpytot += [tpytot_] tpytot += [tpytot_]
...@@ -264,13 +258,14 @@ def speed_multilayer_conv(): ...@@ -264,13 +258,14 @@ def speed_multilayer_conv():
if not tctot_: if not tctot_:
for conv_mode, n_mode in zip(convmodes, xrange(len(convmodes))): for conv_mode, n_mode in zip(convmodes, xrange(len(convmodes))):
for ss, n_ss in zip(ssizes, xrange(len(ssizes))): for ss, n_ss in zip(ssizes, xrange(len(ssizes))):
# tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=0, unroll_kern=0, validate=validate, verbose=verbose,do_print=False) # tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=0, unroll_kern=0, validate=validate, verbose=verbose,do_print=False)
tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=0, unroll_kern=0, verbose=verbose, do_print=False, repeat=repeat) tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=0, unroll_kern=0, verbose=verbose, do_print=False, repeat=repeat)
tctot += [tctot_] tctot += [tctot_]
tpytot += [tpytot_] tpytot += [tpytot_]
ntot += [ntot_] ntot += [ntot_]
else: tctot = N.asarray(tctot_) else:
print("old code timing %.3fs"%sum(tctot), tctot) tctot = N.asarray(tctot_)
print("old code timing %.3fs" % sum(tctot), tctot)
best = N.asarray(best) best = N.asarray(best)
worst = N.asarray(worst) worst = N.asarray(worst)
print("timing for unrolled version") print("timing for unrolled version")
...@@ -278,12 +273,12 @@ def speed_multilayer_conv(): ...@@ -278,12 +273,12 @@ def speed_multilayer_conv():
for n_b in xrange(len(unroll_batch)): for n_b in xrange(len(unroll_batch)):
for n_k in xrange(len(unroll_kern)): for n_k in xrange(len(unroll_kern)):
print((unroll_batch[n_b], unroll_kern[n_k]) + tuple(t[n_b, n_k]), ',') print((unroll_batch[n_b], unroll_kern[n_k]) + tuple(t[n_b, n_k]), ',')
t_detail = t # t_detail = t
t = t.sum(axis=2) t = t.sum(axis=2)
print("max %.3fs"%t.max(), "max param(batch unloop size/kernel unloop size)", t_b_k[t.argmax()]) print("max %.3fs" % t.max(), "max param(batch unloop size/kernel unloop size)", t_b_k[t.argmax()])
print("min %.3fs"%t.min(), "min param(batch unloop size/kernel unloop size)", t_b_k[t.argmin()]) print("min %.3fs" % t.min(), "min param(batch unloop size/kernel unloop size)", t_b_k[t.argmin()])
print("speedup vs (1/1)%.3fx, vs old %.3fx" % (t.max()/t.min(), sum(tctot)/t.min())) print("speedup vs (1/1)%.3fx, vs old %.3fx" % (t.max() / t.min(), sum(tctot) / t.min()))
print(worst/best, tctot/best) print(worst / best, tctot / best)
# calculate the timing of unroll_patch # calculate the timing of unroll_patch
print('time unroll_patch') print('time unroll_patch')
...@@ -291,22 +286,21 @@ def speed_multilayer_conv(): ...@@ -291,22 +286,21 @@ def speed_multilayer_conv():
tctot_patch_size = [] tctot_patch_size = []
for conv_mode, n_mode in zip(convmodes, xrange(len(convmodes))): for conv_mode, n_mode in zip(convmodes, xrange(len(convmodes))):
for ss, n_ss in zip(ssizes, xrange(len(ssizes))): for ss, n_ss in zip(ssizes, xrange(len(ssizes))):
#tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=0, unroll_kern=0, validate=validate,unroll_patch=True,verbose=verbose,do_print=False) # tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=0, unroll_kern=0, validate=validate,unroll_patch=True,verbose=verbose,do_print=False)
tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=0, unroll_kern=0, unroll_patch=True, verbose=verbose, do_print=False, repeat=repeat) tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=0, unroll_kern=0, unroll_patch=True, verbose=verbose, do_print=False, repeat=repeat)
tctot_patch += [tctot_] tctot_patch += [tctot_]
#tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=0, unroll_kern=0, validate=validate,unroll_patch=True,verbose=verbose,do_print=False,unroll_patch_size=True) # tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet_old(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=0, unroll_kern=0, validate=validate,unroll_patch=True,verbose=verbose,do_print=False,unroll_patch_size=True)
tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=0, unroll_kern=0, unroll_patch=True, verbose=verbose, do_print=False, unroll_patch_size=True, repeat=repeat) tctot_, tpytot_, ntot_ = exec_multilayer_conv_nnet(conv_mode, ss, bsize, imshp_start, kshps, nkerns, unroll_batch=0, unroll_kern=0, unroll_patch=True, verbose=verbose, do_print=False, unroll_patch_size=True, repeat=repeat)
tctot_patch_size += [tctot_] tctot_patch_size += [tctot_]
t_patch = sum(tctot_patch) t_patch = sum(tctot_patch)
print("unroll_patch without shape time", tctot_patch) print("unroll_patch without shape time", tctot_patch)
print("speedup vs (1/1)%.3fx, vs old %.3fx" % (t.max()/t_patch, sum(tctot)/t_patch)) print("speedup vs (1/1)%.3fx, vs old %.3fx" % (t.max() / t_patch, sum(tctot) / t_patch))
print(best/tctot_patch, worst/tctot_patch) print(best / tctot_patch, worst / tctot_patch)
t_patch_size = sum(tctot_patch_size) t_patch_size = sum(tctot_patch_size)
print("unroll_patch with shape time", tctot_patch_size) print("unroll_patch with shape time", tctot_patch_size)
print("speedup vs (1/1)%.3fx, vs old %.3fx" % (t.max()/t_patch_size, sum(tctot)/t_patch_size)) print("speedup vs (1/1)%.3fx, vs old %.3fx" % (t.max() / t_patch_size, sum(tctot) / t_patch_size))
print(best/tctot_patch_size, worst/tctot_patch_size) print(best / tctot_patch_size, worst / tctot_patch_size)
return return
if __name__ == '__main__': if __name__ == '__main__':
......
...@@ -49,25 +49,26 @@ class TestConv2D(utt.InferShapeTester): ...@@ -49,25 +49,26 @@ class TestConv2D(utt.InferShapeTester):
""" """
if N_image_shape is None: if N_image_shape is None:
N_image_shape = [T.get_scalar_constant_value(T. N_image_shape = [T.get_scalar_constant_value(
as_tensor_variable(x)) for x in image_shape] T.as_tensor_variable(x)) for x in image_shape]
if N_filter_shape is None: if N_filter_shape is None:
N_filter_shape = [T.get_scalar_constant_value(T. N_filter_shape = [T.get_scalar_constant_value(
as_tensor_variable(x)) for x in filter_shape] T.as_tensor_variable(x)) for x in filter_shape]
if input is None: if input is None:
input = self.input input = self.input
if not filters: if not filters:
filters = self.filters filters = self.filters
############# THEANO IMPLEMENTATION ############ # THEANO IMPLEMENTATION
# we create a symbolic function so that verify_grad can work # we create a symbolic function so that verify_grad can work
def sym_conv2d(input, filters): def sym_conv2d(input, filters):
# define theano graph and function # define theano graph and function
input.name = 'input' input.name = 'input'
filters.name = 'filters' filters.name = 'filters'
rval = conv.conv2d(input, filters, image_shape, filter_shape, rval = conv.conv2d(
input, filters, image_shape, filter_shape,
border_mode, subsample, unroll_batch=unroll_batch, border_mode, subsample, unroll_batch=unroll_batch,
unroll_kern=unroll_kern, unroll_patch=unroll_patch) unroll_kern=unroll_kern, unroll_patch=unroll_patch)
rval.name = 'conv_output' rval.name = 'conv_output'
...@@ -91,7 +92,7 @@ class TestConv2D(utt.InferShapeTester): ...@@ -91,7 +92,7 @@ class TestConv2D(utt.InferShapeTester):
raise Exception( raise Exception(
"ConvOp should have generated an error") "ConvOp should have generated an error")
############# REFERENCE IMPLEMENTATION ############ # REFERENCE IMPLEMENTATION
s = 1. s = 1.
orig_image_data = image_data orig_image_data = image_data
if border_mode is not 'full': if border_mode is not 'full':
...@@ -110,7 +111,8 @@ class TestConv2D(utt.InferShapeTester): ...@@ -110,7 +111,8 @@ class TestConv2D(utt.InferShapeTester):
image_data2 = numpy.zeros((N_image_shape[0], N_image_shape[1], image_data2 = numpy.zeros((N_image_shape[0], N_image_shape[1],
N_image_shape[2] + 2 * N_filter_shape[2] - 2, N_image_shape[2] + 2 * N_filter_shape[2] - 2,
N_image_shape[3] + 2 * N_filter_shape[3] - 2)) N_image_shape[3] + 2 * N_filter_shape[3] - 2))
image_data2[:, :, N_filter_shape[2] - 1:N_filter_shape[2] - 1 + N_image_shape[2], image_data2[
:, :, N_filter_shape[2] - 1:N_filter_shape[2] - 1 + N_image_shape[2],
N_filter_shape[3] - 1:N_filter_shape[3] - 1 + N_image_shape[3]] = image_data N_filter_shape[3] - 1:N_filter_shape[3] - 1 + N_image_shape[3]] = image_data
image_data = image_data2 image_data = image_data2
N_image_shape = image_data.shape N_image_shape = image_data.shape
...@@ -130,7 +132,7 @@ class TestConv2D(utt.InferShapeTester): ...@@ -130,7 +132,7 @@ class TestConv2D(utt.InferShapeTester):
self.assertTrue(_allclose(theano_output, ref_output)) self.assertTrue(_allclose(theano_output, ref_output))
############# TEST GRADIENT ############ # TEST GRADIENT
if verify_grad: if verify_grad:
utt.verify_grad(sym_conv2d, [orig_image_data, filter_data]) utt.verify_grad(sym_conv2d, [orig_image_data, filter_data])
...@@ -157,7 +159,6 @@ class TestConv2D(utt.InferShapeTester): ...@@ -157,7 +159,6 @@ class TestConv2D(utt.InferShapeTester):
def test_uint_image_shape_datatype(self): def test_uint_image_shape_datatype(self):
"""Tests for uint datatype in image_shape. """Tests for uint datatype in image_shape.
""" """
self.validate((2, 2, 3, numpy.uint8(3)), (3, 2, 3, 3), 'valid', verify_grad=False) self.validate((2, 2, 3, numpy.uint8(3)), (3, 2, 3, 3), 'valid', verify_grad=False)
self.validate((numpy.uint16(2), 2, 3, 3), (3, 2, 3, 3), 'valid', verify_grad=False) self.validate((numpy.uint16(2), 2, 3, 3), (3, 2, 3, 3), 'valid', verify_grad=False)
...@@ -181,7 +182,8 @@ class TestConv2D(utt.InferShapeTester): ...@@ -181,7 +182,8 @@ class TestConv2D(utt.InferShapeTester):
""" """
self.validate((3, 2, 7, 5), (5, 2, 2, 3), 'valid', unroll_patch=True) self.validate((3, 2, 7, 5), (5, 2, 2, 3), 'valid', unroll_patch=True)
self.validate((3, 2, 7, 5), (5, 2, 2, 3), 'full', unroll_patch=True) self.validate((3, 2, 7, 5), (5, 2, 2, 3), 'full', unroll_patch=True)
self.validate((3, 2, 3, 3), (4, 2, 3, 3), 'valid', self.validate(
(3, 2, 3, 3), (4, 2, 3, 3), 'valid',
unroll_patch=True, verify_grad=False) unroll_patch=True, verify_grad=False)
def test_unroll_patch_false(self): def test_unroll_patch_false(self):
...@@ -190,20 +192,24 @@ class TestConv2D(utt.InferShapeTester): ...@@ -190,20 +192,24 @@ class TestConv2D(utt.InferShapeTester):
""" """
self.validate((3, 2, 7, 5), (5, 2, 2, 3), 'valid', unroll_patch=False) self.validate((3, 2, 7, 5), (5, 2, 2, 3), 'valid', unroll_patch=False)
self.validate((3, 2, 7, 5), (5, 2, 2, 3), 'full', unroll_patch=False) self.validate((3, 2, 7, 5), (5, 2, 2, 3), 'full', unroll_patch=False)
self.validate((3, 2, 3, 3), (4, 2, 3, 3), 'valid', self.validate(
(3, 2, 3, 3), (4, 2, 3, 3), 'valid',
unroll_patch=False, verify_grad=False) unroll_patch=False, verify_grad=False)
def test_unroll_patch_true_fail(self): def test_unroll_patch_true_fail(self):
""" """
Test basic convs with True. Test basic convs with True.
""" """
self.validate((3, 2, 7, 5), (5, 2, 2, 3), 'valid', unroll_patch=True, self.validate(
(3, 2, 7, 5), (5, 2, 2, 3), 'valid', unroll_patch=True,
N_image_shape=(1, 3, 3, 3), N_filter_shape=(6, 3, 2, 2), N_image_shape=(1, 3, 3, 3), N_filter_shape=(6, 3, 2, 2),
should_raise=True) should_raise=True)
self.validate((3, 2, 7, 5), (5, 2, 2, 3), 'full', unroll_patch=True, self.validate(
(3, 2, 7, 5), (5, 2, 2, 3), 'full', unroll_patch=True,
N_image_shape=(1, 3, 3, 3), N_filter_shape=(6, 3, 2, 2), N_image_shape=(1, 3, 3, 3), N_filter_shape=(6, 3, 2, 2),
should_raise=True) should_raise=True)
self.validate((3, 2, 3, 3), (4, 2, 3, 3), 'valid', unroll_patch=True, self.validate(
(3, 2, 3, 3), (4, 2, 3, 3), 'valid', unroll_patch=True,
N_image_shape=(1, 3, 3, 3), N_filter_shape=(6, 3, 2, 2), N_image_shape=(1, 3, 3, 3), N_filter_shape=(6, 3, 2, 2),
should_raise=True) should_raise=True)
...@@ -218,9 +224,11 @@ class TestConv2D(utt.InferShapeTester): ...@@ -218,9 +224,11 @@ class TestConv2D(utt.InferShapeTester):
Test mini-batch unrolling for various legal values. Test mini-batch unrolling for various legal values.
""" """
# mini-batch of size 6 is multiple of 2 and 3. Should work. # mini-batch of size 6 is multiple of 2 and 3. Should work.
self.validate((6, 2, 3, 3), (3, 2, 2, 2), 'valid', self.validate(
(6, 2, 3, 3), (3, 2, 2, 2), 'valid',
unroll_batch=2, verify_grad=False) unroll_batch=2, verify_grad=False)
self.validate((6, 2, 3, 3), (3, 2, 2, 2), 'valid', self.validate(
(6, 2, 3, 3), (3, 2, 2, 2), 'valid',
unroll_batch=3, verify_grad=False) unroll_batch=3, verify_grad=False)
def test_unroll_kern(self): def test_unroll_kern(self):
...@@ -228,9 +236,11 @@ class TestConv2D(utt.InferShapeTester): ...@@ -228,9 +236,11 @@ class TestConv2D(utt.InferShapeTester):
Test kernel unrolling for various legal values. Test kernel unrolling for various legal values.
""" """
# 6 filters is a multiple of 2 and 3. Should work. # 6 filters is a multiple of 2 and 3. Should work.
self.validate((2, 3, 3, 3), (6, 3, 2, 2), 'valid', unroll_kern=2, self.validate(
(2, 3, 3, 3), (6, 3, 2, 2), 'valid', unroll_kern=2,
verify_grad=False) verify_grad=False)
self.validate((2, 3, 3, 3), (6, 3, 2, 2), 'valid', unroll_kern=3, self.validate(
(2, 3, 3, 3), (6, 3, 2, 2), 'valid', unroll_kern=3,
verify_grad=False) verify_grad=False)
def test_unroll_batch_kern(self): def test_unroll_batch_kern(self):
...@@ -239,14 +249,18 @@ class TestConv2D(utt.InferShapeTester): ...@@ -239,14 +249,18 @@ class TestConv2D(utt.InferShapeTester):
""" """
# mini-batch of size 6 is multiple of 2 and 3. Should work. # mini-batch of size 6 is multiple of 2 and 3. Should work.
self.validate((6, 2, 3, 3), (3, 2, 2, 2), 'valid', self.validate(
(6, 2, 3, 3), (3, 2, 2, 2), 'valid',
unroll_batch=2, unroll_kern=3, verify_grad=False) unroll_batch=2, unroll_kern=3, verify_grad=False)
self.validate((6, 2, 3, 3), (3, 2, 2, 2), 'valid', self.validate(
(6, 2, 3, 3), (3, 2, 2, 2), 'valid',
unroll_batch=3, unroll_kern=3, verify_grad=False) unroll_batch=3, unroll_kern=3, verify_grad=False)
# 6 filters is a multiple of 2 and 3. Should work. # 6 filters is a multiple of 2 and 3. Should work.
self.validate((2, 3, 3, 3), (6, 3, 2, 2), 'valid', self.validate(
(2, 3, 3, 3), (6, 3, 2, 2), 'valid',
unroll_batch=2, unroll_kern=2, verify_grad=False) unroll_batch=2, unroll_kern=2, verify_grad=False)
self.validate((2, 3, 3, 3), (6, 3, 2, 2), 'valid', self.validate(
(2, 3, 3, 3), (6, 3, 2, 2), 'valid',
unroll_batch=2, unroll_kern=3, verify_grad=False) unroll_batch=2, unroll_kern=3, verify_grad=False)
def test_unroll_batch_kern_fail(self): def test_unroll_batch_kern_fail(self):
...@@ -264,11 +278,13 @@ class TestConv2D(utt.InferShapeTester): ...@@ -264,11 +278,13 @@ class TestConv2D(utt.InferShapeTester):
unroll_batch=3, unroll_kern=3, unroll_batch=3, unroll_kern=3,
N_image_shape=(6, 2, 3, 3), N_filter_shape=(4, 2, 2, 2), N_image_shape=(6, 2, 3, 3), N_filter_shape=(4, 2, 2, 2),
should_raise=True) should_raise=True)
self.validate((2, 3, 3, 3), (6, 3, 2, 2), 'valid', self.validate(
(2, 3, 3, 3), (6, 3, 2, 2), 'valid',
unroll_batch=2, unroll_kern=2, unroll_batch=2, unroll_kern=2,
N_image_shape=(1, 3, 3, 3), N_filter_shape=(6, 3, 2, 2), N_image_shape=(1, 3, 3, 3), N_filter_shape=(6, 3, 2, 2),
should_raise=True) should_raise=True)
self.validate((2, 3, 3, 3), (6, 3, 2, 2), 'valid', self.validate(
(2, 3, 3, 3), (6, 3, 2, 2), 'valid',
unroll_batch=2, unroll_kern=3, unroll_batch=2, unroll_kern=3,
N_image_shape=(2, 3, 3, 3), N_filter_shape=(5, 3, 2, 2), N_image_shape=(2, 3, 3, 3), N_filter_shape=(5, 3, 2, 2),
should_raise=True) should_raise=True)
...@@ -292,11 +308,13 @@ class TestConv2D(utt.InferShapeTester): ...@@ -292,11 +308,13 @@ class TestConv2D(utt.InferShapeTester):
Tests convolution where the {image,filter}_shape is a Constant tensor. Tests convolution where the {image,filter}_shape is a Constant tensor.
""" """
as_t = T.as_tensor_variable as_t = T.as_tensor_variable
self.validate((as_t(3), as_t(2), as_t(7), as_t(5)), (5, 2, self.validate(
2, 3), 'valid') (as_t(3), as_t(2), as_t(7), as_t(5)), (5, 2, 2, 3), 'valid')
self.validate(as_t([3, 2, 7, 5]), (5, 2, 2, 3), 'valid') self.validate(as_t([3, 2, 7, 5]), (5, 2, 2, 3), 'valid')
self.validate(as_t((3, 2, 7, 5)), (5, 2, 2, 3), 'valid') self.validate(as_t((3, 2, 7, 5)), (5, 2, 2, 3), 'valid')
self.validate((3, 2, 7, 5), (as_t(5), as_t(2), as_t(2), self.validate(
(3, 2, 7, 5), (
as_t(5), as_t(2), as_t(2),
as_t(3)), 'valid') as_t(3)), 'valid')
self.validate((3, 2, 7, 5), as_t([5, 2, 2, 3]), 'valid') self.validate((3, 2, 7, 5), as_t([5, 2, 2, 3]), 'valid')
self.validate((3, 2, 7, 5), as_t((5, 2, 2, 3)), 'valid') self.validate((3, 2, 7, 5), as_t((5, 2, 2, 3)), 'valid')
...@@ -444,10 +462,11 @@ class TestConv2D(utt.InferShapeTester): ...@@ -444,10 +462,11 @@ class TestConv2D(utt.InferShapeTester):
print(border_mode) print(border_mode)
for openmp in [False, True]: for openmp in [False, True]:
print("OpenMP", openmp) print("OpenMP", openmp)
image_shapes = [(1, 5, 6, 6), image_shapes = [
(10, 5, 6, 6), (1, 5, 6, 6),
#(10, 10, 16, 16), (10, 5, 6, 6)
#(10, 10, 32, 32) # (10, 10, 16, 16),
# (10, 10, 32, 32)]
] ]
print("image_shape", image_shapes) print("image_shape", image_shapes)
for image_shape in image_shapes: for image_shape in image_shapes:
...@@ -458,7 +477,8 @@ class TestConv2D(utt.InferShapeTester): ...@@ -458,7 +477,8 @@ class TestConv2D(utt.InferShapeTester):
input = theano.shared(numpy.random.random(image_shape)) input = theano.shared(numpy.random.random(image_shape))
filters = theano.shared(numpy.random.random(filter_shape)) filters = theano.shared(numpy.random.random(filter_shape))
output = self.conv2d(input, filters, output = self.conv2d(
input, filters,
image_shape, filter_shape, image_shape, filter_shape,
border_mode, border_mode,
unroll_patch=True, unroll_patch=True,
...@@ -487,70 +507,100 @@ class TestConv2D(utt.InferShapeTester): ...@@ -487,70 +507,100 @@ class TestConv2D(utt.InferShapeTester):
bivec_val = [7, 5, 3, 2] bivec_val = [7, 5, 3, 2]
adtens_val = rand(*aivec_val) adtens_val = rand(*aivec_val)
bdtens_val = rand(*bivec_val) bdtens_val = rand(*bivec_val)
self._compile_and_check([adtens, bdtens], self._compile_and_check(
[self.conv2d(adtens, bdtens, aivec_val, bivec_val, [adtens, bdtens],
border_mode='valid')], [adtens_val, bdtens_val], conv.ConvOp, [self.conv2d(
adtens, bdtens, aivec_val, bivec_val,
border_mode='valid')],
[adtens_val, bdtens_val], conv.ConvOp,
excluding=['conv_gemm']) excluding=['conv_gemm'])
self._compile_and_check([adtens, bdtens], self._compile_and_check(
[self.conv2d(adtens, bdtens, aivec_val, bivec_val, [adtens, bdtens],
border_mode='full')], [adtens_val, bdtens_val], conv.ConvOp, [self.conv2d(
adtens, bdtens, aivec_val, bivec_val,
border_mode='full')],
[adtens_val, bdtens_val], conv.ConvOp,
excluding=['conv_gemm']) excluding=['conv_gemm'])
aivec_val = [6, 2, 8, 3] aivec_val = [6, 2, 8, 3]
bivec_val = [4, 2, 5, 3] bivec_val = [4, 2, 5, 3]
adtens_val = rand(*aivec_val) adtens_val = rand(*aivec_val)
bdtens_val = rand(*bivec_val) bdtens_val = rand(*bivec_val)
self._compile_and_check([adtens, bdtens], self._compile_and_check(
[self.conv2d(adtens, bdtens, aivec_val, bivec_val, [adtens, bdtens],
border_mode='valid')], [adtens_val, bdtens_val], conv.ConvOp, [self.conv2d(
adtens, bdtens, aivec_val, bivec_val,
border_mode='valid')],
[adtens_val, bdtens_val], conv.ConvOp,
excluding=['conv_gemm']) excluding=['conv_gemm'])
self._compile_and_check([adtens, bdtens], self._compile_and_check(
[self.conv2d(adtens, bdtens, aivec_val, bivec_val, [adtens, bdtens],
border_mode='full')], [adtens_val, bdtens_val], conv.ConvOp, [self.conv2d(
adtens, bdtens, aivec_val, bivec_val,
border_mode='full')],
[adtens_val, bdtens_val], conv.ConvOp,
excluding=['conv_gemm']) excluding=['conv_gemm'])
aivec_val = [3, 6, 7, 5] aivec_val = [3, 6, 7, 5]
bivec_val = [5, 6, 3, 2] bivec_val = [5, 6, 3, 2]
adtens_val = rand(*aivec_val) adtens_val = rand(*aivec_val)
bdtens_val = rand(*bivec_val) bdtens_val = rand(*bivec_val)
self._compile_and_check([adtens, bdtens], self._compile_and_check(
[self.conv2d(adtens, bdtens, aivec_val, bivec_val, [adtens, bdtens],
border_mode='valid')], [adtens_val, bdtens_val], conv.ConvOp, [self.conv2d(
adtens, bdtens, aivec_val, bivec_val,
border_mode='valid')],
[adtens_val, bdtens_val], conv.ConvOp,
excluding=['conv_gemm']) excluding=['conv_gemm'])
self._compile_and_check([adtens, bdtens], self._compile_and_check(
[self.conv2d(adtens, bdtens, aivec_val, bivec_val, [adtens, bdtens],
border_mode='full')], [adtens_val, bdtens_val], conv.ConvOp, [self.conv2d(
adtens, bdtens, aivec_val, bivec_val,
border_mode='full')],
[adtens_val, bdtens_val], conv.ConvOp,
excluding=['conv_gemm']) excluding=['conv_gemm'])
aivec_val = [3, 6, 7, 5] aivec_val = [3, 6, 7, 5]
bivec_val = [5, 6, 2, 3] bivec_val = [5, 6, 2, 3]
adtens_val = rand(*aivec_val) adtens_val = rand(*aivec_val)
bdtens_val = rand(*bivec_val) bdtens_val = rand(*bivec_val)
self._compile_and_check([adtens, bdtens], self._compile_and_check(
[self.conv2d(adtens, bdtens, aivec_val, bivec_val, [adtens, bdtens],
border_mode='valid')], [adtens_val, bdtens_val], conv.ConvOp, [self.conv2d(
adtens, bdtens, aivec_val, bivec_val,
border_mode='valid')],
[adtens_val, bdtens_val], conv.ConvOp,
excluding=['conv_gemm']) excluding=['conv_gemm'])
self._compile_and_check([adtens, bdtens], self._compile_and_check(
[self.conv2d(adtens, bdtens, aivec_val, bivec_val, [adtens, bdtens],
border_mode='full')], [adtens_val, bdtens_val], conv.ConvOp, [self.conv2d(
adtens, bdtens, aivec_val, bivec_val,
border_mode='full')],
[adtens_val, bdtens_val], conv.ConvOp,
excluding=['conv_gemm']) excluding=['conv_gemm'])
aivec_val = [5, 2, 4, 3] aivec_val = [5, 2, 4, 3]
bivec_val = [6, 2, 4, 3] bivec_val = [6, 2, 4, 3]
adtens_val = rand(*aivec_val) adtens_val = rand(*aivec_val)
bdtens_val = rand(*bivec_val) bdtens_val = rand(*bivec_val)
self._compile_and_check([adtens, bdtens], self._compile_and_check(
[self.conv2d(adtens, bdtens, aivec_val, bivec_val, [adtens, bdtens],
border_mode='valid')], [adtens_val, bdtens_val], conv.ConvOp, [self.conv2d(
adtens, bdtens, aivec_val, bivec_val,
border_mode='valid')],
[adtens_val, bdtens_val], conv.ConvOp,
excluding=['conv_gemm']) excluding=['conv_gemm'])
self._compile_and_check([adtens, bdtens], self._compile_and_check(
[self.conv2d(adtens, bdtens, aivec_val, bivec_val, [adtens, bdtens],
border_mode='full')], [adtens_val, bdtens_val], conv.ConvOp, [self.conv2d(
adtens, bdtens, aivec_val, bivec_val,
border_mode='full')],
[adtens_val, bdtens_val], conv.ConvOp,
excluding=['conv_gemm']) excluding=['conv_gemm'])
...@@ -560,17 +610,19 @@ class TestDefaultConv2D(TestConv2D): ...@@ -560,17 +610,19 @@ class TestDefaultConv2D(TestConv2D):
# Test that broadcasting of gradients works correctly when using the # Test that broadcasting of gradients works correctly when using the
# nnet.conv2d() interface. This was reported in #3763, and uses the example # nnet.conv2d() interface. This was reported in #3763, and uses the example
# code from that ticket. # code from that ticket.
def test_broadcast_grad(): def test_broadcast_grad():
rng = numpy.random.RandomState(utt.fetch_seed()) # rng = numpy.random.RandomState(utt.fetch_seed())
x1 = T.tensor4('x') x1 = T.tensor4('x')
x1_data = rng.randn(1, 1, 300, 300) # x1_data = rng.randn(1, 1, 300, 300)
sigma = T.scalar('sigma') sigma = T.scalar('sigma')
sigma_data = 20 # sigma_data = 20
window_radius = 3 window_radius = 3
filter_1d = T.arange(-window_radius, window_radius+1) filter_1d = T.arange(-window_radius, window_radius + 1)
filter_1d = filter_1d.astype(theano.config.floatX) filter_1d = filter_1d.astype(theano.config.floatX)
filter_1d = T.exp(-0.5*filter_1d**2/sigma**2) filter_1d = T.exp(-0.5 * filter_1d**2 / sigma ** 2)
filter_1d = filter_1d / filter_1d.sum() filter_1d = filter_1d / filter_1d.sum()
filter_W = filter_1d.dimshuffle(['x', 'x', 0, 'x']) filter_W = filter_1d.dimshuffle(['x', 'x', 0, 'x'])
......
from __future__ import absolute_import, print_function, division from __future__ import absolute_import, print_function, division
import unittest
import theano import theano
import theano.tensor as T import theano.tensor as T
from theano import function, shared from theano import function, shared
...@@ -8,13 +7,13 @@ from theano.tensor.nnet.ConvTransp3D import convTransp3D, ConvTransp3D ...@@ -8,13 +7,13 @@ from theano.tensor.nnet.ConvTransp3D import convTransp3D, ConvTransp3D
from theano.tensor.nnet.ConvGrad3D import convGrad3D, ConvGrad3D from theano.tensor.nnet.ConvGrad3D import convGrad3D, ConvGrad3D
from theano.tensor.nnet.Conv3D import conv3D, Conv3D from theano.tensor.nnet.Conv3D import conv3D, Conv3D
from theano.tests.unittest_tools import attr from theano.tests.unittest_tools import attr
from nose.plugins.skip import SkipTest
import numpy as N import numpy as N
from six.moves import xrange from six.moves import xrange
import copy import copy
import theano.sparse import theano.sparse
if theano.sparse.enable_sparse: if theano.sparse.enable_sparse:
from scipy import sparse from scipy import sparse
from nose.plugins.skip import SkipTest
floatX = theano.config.floatX floatX = theano.config.floatX
...@@ -74,8 +73,8 @@ class DummyConvGrad3D: ...@@ -74,8 +73,8 @@ class DummyConvGrad3D:
self.V, self.dCdH = VdHvals self.V, self.dCdH = VdHvals
self.dV = shared(rng.uniform(-1, 1, self.dV = shared(rng.uniform(-1, 1,
self.V.get_value(borrow=True).shape)) self.V.get_value(borrow=True).shape))
self.ddCdH = shared(rng.uniform(-1, 1, self.ddCdH = shared(rng.uniform(
self.dCdH.get_value(borrow=True).shape)) -1, 1, self.dCdH.get_value(borrow=True).shape))
self.d = d self.d = d
self.WShape = WShape self.WShape = WShape
...@@ -142,8 +141,8 @@ class TestConv3D(utt.InferShapeTester): ...@@ -142,8 +141,8 @@ class TestConv3D(utt.InferShapeTester):
self.RShape = T.vector(dtype='int64') self.RShape = T.vector(dtype='int64')
self.RShape.name = 'RShape' self.RShape.name = 'RShape'
self.otherH = T.TensorType(floatX, self.otherH = T.TensorType(
(False, False, False, False, False))(name='otherH') floatX, (False, False, False, False, False))(name='otherH')
self.transp = convTransp3D(self.W, self.rb, self.d, self.transp = convTransp3D(self.W, self.rb, self.d,
self.otherH, self.RShape) self.otherH, self.RShape)
self.transp.name = 'transp' self.transp.name = 'transp'
...@@ -165,18 +164,17 @@ class TestConv3D(utt.InferShapeTester): ...@@ -165,18 +164,17 @@ class TestConv3D(utt.InferShapeTester):
W_grad = T.grad(self.reconsObj, self.W) W_grad = T.grad(self.reconsObj, self.W)
self.gradientsFunc = function([self.RShape], self.gradientsFunc = function(
[W_grad, T.grad(self.reconsObj, [self.RShape],
self.H), T.grad(self.reconsObj, self.V), [W_grad, T.grad(self.reconsObj, self.H), T.grad(self.reconsObj, self.V),
T.grad(self.reconsObj, self.b)], mode=mode) T.grad(self.reconsObj, self.b)], mode=mode)
self.check_c_against_python = function([self.RShape], self.check_c_against_python = function(
[T.grad(self.reconsObj, self.W), T.grad(self.reconsObj, [self.RShape],
self.H), T.grad(self.reconsObj, self.V), [T.grad(self.reconsObj, self.W), T.grad(self.reconsObj, self.H), T.grad(self.reconsObj, self.V),
T.grad(self.reconsObj, self.b)], mode='DEBUG_MODE') T.grad(self.reconsObj, self.b)], mode='DEBUG_MODE')
self.dCdW_shape_func = function([self.RShape], self.dCdW_shape_func = function([self.RShape], T.grad(self.reconsObj, self.W).shape, mode=mode)
T.grad(self.reconsObj, self.W).shape, mode=mode)
def random_tensor(self, *dims): def random_tensor(self, *dims):
return N.asarray(self.rng.uniform(-.05, .05, dims), dtype=floatX) return N.asarray(self.rng.uniform(-.05, .05, dims), dtype=floatX)
...@@ -205,19 +203,21 @@ class TestConv3D(utt.InferShapeTester): ...@@ -205,19 +203,21 @@ class TestConv3D(utt.InferShapeTester):
self.d.get_value(borrow=True, return_internal_type=True)[2] = \ self.d.get_value(borrow=True, return_internal_type=True)[2] = \
self.rng.randint(1, 15) self.rng.randint(1, 15)
outputHeight = int((videoHeight - filterHeight) / int((videoHeight - filterHeight) /
self.d.get_value(borrow=True)[0]) + 1 self.d.get_value(borrow=True)[0]) + 1
outputWidth = int((videoWidth - filterWidth) / int((videoWidth - filterWidth) /
self.d.get_value(borrow=True)[1]) + 1 self.d.get_value(borrow=True)[1]) + 1
outputDur = int((videoDur - filterDur) / int((videoDur - filterDur) /
self.d.get_value(borrow=True)[2]) + 1 self.d.get_value(borrow=True)[2]) + 1
self.W.set_value(self.random_tensor(numFilters, filterHeight, self.W.set_value(self.random_tensor(
numFilters, filterHeight,
filterWidth, filterDur, inputChannels), borrow=True) filterWidth, filterDur, inputChannels), borrow=True)
self.b.set_value(self.random_tensor(numFilters), borrow=True) self.b.set_value(self.random_tensor(numFilters), borrow=True)
self.rb.set_value(self.random_tensor(inputChannels), borrow=True) self.rb.set_value(self.random_tensor(inputChannels), borrow=True)
self.V.set_value(self.random_tensor(batchSize, videoHeight, self.V.set_value(self.random_tensor(
batchSize, videoHeight,
videoWidth, videoDur, inputChannels), borrow=True) videoWidth, videoDur, inputChannels), borrow=True)
self.rb.set_value(self.random_tensor(inputChannels), borrow=True) self.rb.set_value(self.random_tensor(inputChannels), borrow=True)
...@@ -250,15 +250,17 @@ class TestConv3D(utt.InferShapeTester): ...@@ -250,15 +250,17 @@ class TestConv3D(utt.InferShapeTester):
self.d.get_value(borrow=True, return_internal_type=True)[2] = \ self.d.get_value(borrow=True, return_internal_type=True)[2] = \
self.rng.randint(1, 15) self.rng.randint(1, 15)
self.W.set_value(self.random_tensor(numFilters, filterHeight, self.W.set_value(self.random_tensor(
numFilters, filterHeight,
filterWidth, filterDur, inputChannels), borrow=True) filterWidth, filterDur, inputChannels), borrow=True)
self.W.set_value(self.W.get_value(borrow=True) * self.W.set_value(
self.W.get_value(borrow=True) *
(self.W.get_value(borrow=True) < 1e-5), borrow=True) (self.W.get_value(borrow=True) < 1e-5), borrow=True)
self.b.set_value(self.random_tensor(numFilters), borrow=True) self.b.set_value(self.random_tensor(numFilters), borrow=True)
self.V.set_value(self.random_tensor(batchSize, videoHeight, self.V.set_value(self.random_tensor(
videoWidth, videoDur, inputChannels), borrow=True) batchSize, videoHeight, videoWidth, videoDur, inputChannels), borrow=True)
Hv = self.H_func() Hv = self.H_func()
...@@ -288,9 +290,9 @@ class TestConv3D(utt.InferShapeTester): ...@@ -288,9 +290,9 @@ class TestConv3D(utt.InferShapeTester):
print(H_mat) print(H_mat)
print(Hv_mat) print(Hv_mat)
print('max error: ' + str(N.abs(H_mat - Hv_mat).max())) print('max error: ' + str(N.abs(H_mat - Hv_mat).max()))
W.get_value(borrow=True)[W.get_value(borrow=True) != 0] += 1.0 self.W.get_value(borrow=True)[self.W.get_value(borrow=True) != 0] += 1.0
print('min non-zero kernel mag: ' + \ print('min non-zero kernel mag: ' + str(
str(N.abs(W.get_value(borrow=True)).min())) N.abs(self.W.get_value(borrow=True)).min()))
assert False assert False
def test_c_against_mat_transp_mul(self): def test_c_against_mat_transp_mul(self):
...@@ -315,12 +317,14 @@ class TestConv3D(utt.InferShapeTester): ...@@ -315,12 +317,14 @@ class TestConv3D(utt.InferShapeTester):
self.d.get_value(borrow=True, return_internal_type=True)[2] = \ self.d.get_value(borrow=True, return_internal_type=True)[2] = \
self.rng.randint(1, 15) self.rng.randint(1, 15)
self.W.set_value(self.random_tensor(numFilters, filterHeight, self.W.set_value(self.random_tensor(
numFilters, filterHeight,
filterWidth, filterDur, inputChannels), borrow=True) filterWidth, filterDur, inputChannels), borrow=True)
self.b.set_value(self.random_tensor(numFilters), borrow=True) self.b.set_value(self.random_tensor(numFilters), borrow=True)
self.V.set_value(self.random_tensor(batchSize, videoHeight, self.V.set_value(self.random_tensor(
batchSize, videoHeight,
videoWidth, videoDur, inputChannels), borrow=True) videoWidth, videoDur, inputChannels), borrow=True)
self.rb.set_value(self.random_tensor(inputChannels), borrow=True) self.rb.set_value(self.random_tensor(inputChannels), borrow=True)
...@@ -330,7 +334,7 @@ class TestConv3D(utt.InferShapeTester): ...@@ -330,7 +334,7 @@ class TestConv3D(utt.InferShapeTester):
assert H_shape[2] == 1 assert H_shape[2] == 1
assert H_shape[3] == 1 assert H_shape[3] == 1
Hv = self.random_tensor( * H_shape) Hv = self.random_tensor(* H_shape)
Vv = self.transp_func(Hv, [videoHeight, videoWidth, videoDur]) Vv = self.transp_func(Hv, [videoHeight, videoWidth, videoDur])
...@@ -349,7 +353,7 @@ class TestConv3D(utt.InferShapeTester): ...@@ -349,7 +353,7 @@ class TestConv3D(utt.InferShapeTester):
for qi in xrange(0, batchSize): for qi in xrange(0, batchSize):
Vv_mat[:, qi] = Vv[qi, :, :, :, :].reshape((n)) Vv_mat[:, qi] = Vv[qi, :, :, :, :].reshape((n))
V_mat = (N.dot(W_mat.transpose(), Hv_mat).transpose() + \ V_mat = (N.dot(W_mat.transpose(), Hv_mat).transpose() +
rbv).transpose() rbv).transpose()
if N.abs(V_mat - Vv_mat).max() > 1e-5: if N.abs(V_mat - Vv_mat).max() > 1e-5:
...@@ -359,7 +363,8 @@ class TestConv3D(utt.InferShapeTester): ...@@ -359,7 +363,8 @@ class TestConv3D(utt.InferShapeTester):
for qq in xrange(V_mat.shape[0]): for qq in xrange(V_mat.shape[0]):
for qqq in xrange(Vv_mat.shape[1]): for qqq in xrange(Vv_mat.shape[1]):
if abs(V_mat[qq, qqq] - Vv_mat[qq, qqq]) > 1e-5: if abs(V_mat[qq, qqq] - Vv_mat[qq, qqq]) > 1e-5:
print(('wrong at ' + str((qq, qqq)) + ': ' + print(
('wrong at ' + str((qq, qqq)) + ': ' +
str(V_mat[qq, qqq], Vv_mat[qq, qqq]))) str(V_mat[qq, qqq], Vv_mat[qq, qqq])))
assert False assert False
...@@ -390,22 +395,21 @@ class TestConv3D(utt.InferShapeTester): ...@@ -390,22 +395,21 @@ class TestConv3D(utt.InferShapeTester):
col_steps = self.rng.randint(1, 4) col_steps = self.rng.randint(1, 4)
time_steps = self.rng.randint(1, 4) time_steps = self.rng.randint(1, 4)
#print (row_steps,col_steps,time_steps) # print (row_steps,col_steps,time_steps)
videoDur = (time_steps - 1) * dt + filterDur + \ videoDur = (time_steps - 1) * dt + filterDur + self.rng.randint(0, 3)
self.rng.randint(0, 3) videoWidth = (col_steps - 1) * dc + filterWidth + self.rng.randint(0, 3)
videoWidth = (col_steps - 1) * dc + filterWidth + \ videoHeight = (row_steps - 1) * dr + filterHeight + self.rng.randint(0, 3)
self.rng.randint(0, 3)
videoHeight = (row_steps - 1) * dr + filterHeight + \
self.rng.randint(0, 3)
inputChannels = self.rng.randint(1, 15) inputChannels = self.rng.randint(1, 15)
self.W.set_value(self.random_tensor(numFilters, filterHeight, self.W.set_value(self.random_tensor(
numFilters, filterHeight,
filterWidth, filterDur, inputChannels), borrow=True) filterWidth, filterDur, inputChannels), borrow=True)
self.b.set_value(self.random_tensor(numFilters), borrow=True) self.b.set_value(self.random_tensor(numFilters), borrow=True)
# just needed so H_shape works # just needed so H_shape works
self.V.set_value(self.random_tensor(batchSize, videoHeight, videoWidth, self.V.set_value(self.random_tensor(
batchSize, videoHeight, videoWidth,
videoDur, inputChannels), borrow=True) videoDur, inputChannels), borrow=True)
self.rb.set_value(self.random_tensor(inputChannels), borrow=True) self.rb.set_value(self.random_tensor(inputChannels), borrow=True)
...@@ -488,14 +492,15 @@ class TestConv3D(utt.InferShapeTester): ...@@ -488,14 +492,15 @@ class TestConv3D(utt.InferShapeTester):
self._compile_and_check([], [self.H], [], Conv3D) self._compile_and_check([], [self.H], [], Conv3D)
# ConvTransp3D # ConvTransp3D
self._compile_and_check([self.RShape], [self.R], self._compile_and_check(
[self.RShape], [self.R],
[self.V.get_value(borrow=True).shape[1:4]], ConvTransp3D) [self.V.get_value(borrow=True).shape[1:4]], ConvTransp3D)
# ConvGrad3D # ConvGrad3D
self._compile_and_check([self.RShape], [T.grad(self.reconsObj, self.W), self._compile_and_check(
T.grad(self.reconsObj, self.H), [self.RShape],
T.grad(self.reconsObj, self.V), [T.grad(self.reconsObj, self.W), T.grad(self.reconsObj, self.H),
T.grad(self.reconsObj, self.b)], T.grad(self.reconsObj, self.V), T.grad(self.reconsObj, self.b)],
[self.V.get_value(borrow=True).shape[1:4]], ConvGrad3D) [self.V.get_value(borrow=True).shape[1:4]], ConvGrad3D)
def test_gradient(self): def test_gradient(self):
...@@ -503,13 +508,15 @@ class TestConv3D(utt.InferShapeTester): ...@@ -503,13 +508,15 @@ class TestConv3D(utt.InferShapeTester):
rng, V, W, b, d, rb = self.rng, self.V, self.W, self.b, self.d, self.rb rng, V, W, b, d, rb = self.rng, self.V, self.W, self.b, self.d, self.rb
dCdH = shared(self.random_tensor(*self.H_shape_func())) dCdH = shared(self.random_tensor(*self.H_shape_func()))
testsPerDir = 2 testsPerDir = 2
theano.tests.unittest_tools.verify_grad(DummyConv3D(rng, (V, W, b), d), theano.tests.unittest_tools.verify_grad(DummyConv3D(
[0.0], n_tests=testsPerDir) rng, (V, W, b), d), [0.0], n_tests=testsPerDir)
theano.tests.unittest_tools.verify_grad(DummyConvTransp3D(rng, theano.tests.unittest_tools.verify_grad(
(W, rb, dCdH), d, V.get_value(borrow=True).shape[1:4]), DummyConvTransp3D(
rng, (W, rb, dCdH), d, V.get_value(borrow=True).shape[1:4]),
[0.0], n_tests=testsPerDir) [0.0], n_tests=testsPerDir)
theano.tests.unittest_tools.verify_grad(DummyConvGrad3D(rng, (V, dCdH), theano.tests.unittest_tools.verify_grad(
d, W.get_value(borrow=True).shape), DummyConvGrad3D(
rng, (V, dCdH), d, W.get_value(borrow=True).shape),
[0.0], n_tests=testsPerDir) [0.0], n_tests=testsPerDir)
......
...@@ -11,7 +11,7 @@ from six.moves import xrange ...@@ -11,7 +11,7 @@ from six.moves import xrange
import theano import theano
from theano.gof.opt import check_stack_trace from theano.gof.opt import check_stack_trace
from theano.tensor.nnet.conv3d2d import * from theano.tensor.nnet.conv3d2d import conv3d, get_diagonal_subtensor_view, DiagonalSubtensor, IncDiagonalSubtensor
import theano.tests.unittest_tools as utt import theano.tests.unittest_tools as utt
...@@ -57,11 +57,11 @@ def pyconv3d(signals, filters): ...@@ -57,11 +57,11 @@ def pyconv3d(signals, filters):
Ns, Ts, C, Hs, Ws = signals.shape Ns, Ts, C, Hs, Ws = signals.shape
Nf, Tf, C, Hf, Wf = filters.shape Nf, Tf, C, Hf, Wf = filters.shape
Tf2 = Tf//2 Tf2 = Tf // 2
Hf2 = Hf//2 Hf2 = Hf // 2
Wf2 = Wf//2 Wf2 = Wf // 2
rval = numpy.zeros((Ns, Ts-Tf+1, Nf, Hs-Hf+1, Ws-Wf+1)) rval = numpy.zeros((Ns, Ts - Tf + 1, Nf, Hs - Hf + 1, Ws - Wf + 1))
for ns in xrange(Ns): for ns in xrange(Ns):
for nf in xrange(Nf): for nf in xrange(Nf):
for c in xrange(C): for c in xrange(C):
...@@ -71,7 +71,7 @@ def pyconv3d(signals, filters): ...@@ -71,7 +71,7 @@ def pyconv3d(signals, filters):
o_i = ndimage.convolve(s_i, f_i, mode='constant', cval=1) o_i = ndimage.convolve(s_i, f_i, mode='constant', cval=1)
o_i_sh0 = o_i.shape[0] o_i_sh0 = o_i.shape[0]
# print s_i.shape, f_i.shape, r_i.shape, o_i.shape # print s_i.shape, f_i.shape, r_i.shape, o_i.shape
r_i += o_i[Tf2:o_i_sh0-Tf2, Hf2:-Hf2, Wf2:-Wf2] r_i += o_i[Tf2:o_i_sh0 - Tf2, Hf2:-Hf2, Wf2:-Wf2]
return rval return rval
...@@ -85,10 +85,10 @@ def test_conv3d(mode=mode_without_gpu, shared=theano.tensor._shared): ...@@ -85,10 +85,10 @@ def test_conv3d(mode=mode_without_gpu, shared=theano.tensor._shared):
raise SkipTest("conv3d2d tests need SciPy") raise SkipTest("conv3d2d tests need SciPy")
Ns, Ts, C, Hs, Ws = 3, 10, 3, 32, 32 Ns, Ts, C, Hs, Ws = 3, 10, 3, 32, 32
Nf, Tf, C, Hf, Wf = 32, 5 , 3, 5 , 5 Nf, Tf, C, Hf, Wf = 32, 5, 3, 5, 5
signals = numpy.arange(Ns*Ts*C*Hs*Ws).reshape(Ns, Ts, C, Hs, Ws).astype('float32') signals = numpy.arange(Ns * Ts * C * Hs * Ws).reshape(Ns, Ts, C, Hs, Ws).astype('float32')
filters = numpy.arange(Nf*Tf*C*Hf*Wf).reshape(Nf, Tf, C, Hf, Wf).astype('float32') filters = numpy.arange(Nf * Tf * C * Hf * Wf).reshape(Nf, Tf, C, Hf, Wf).astype('float32')
t0 = time.time() t0 = time.time()
pyres = pyconv3d(signals, filters) pyres = pyconv3d(signals, filters)
...@@ -96,7 +96,7 @@ def test_conv3d(mode=mode_without_gpu, shared=theano.tensor._shared): ...@@ -96,7 +96,7 @@ def test_conv3d(mode=mode_without_gpu, shared=theano.tensor._shared):
s_signals = shared(signals) s_signals = shared(signals)
s_filters = shared(filters) s_filters = shared(filters)
s_output = shared(signals*0) s_output = shared(signals * 0)
out = conv3d(s_signals, s_filters, out = conv3d(s_signals, s_filters,
signals_shape=signals.shape, signals_shape=signals.shape,
...@@ -130,12 +130,12 @@ def test_conv3d(mode=mode_without_gpu, shared=theano.tensor._shared): ...@@ -130,12 +130,12 @@ def test_conv3d(mode=mode_without_gpu, shared=theano.tensor._shared):
filters = numpy.random.rand(Nf, Tf, C, Hf, Wf).astype('float32') filters = numpy.random.rand(Nf, Tf, C, Hf, Wf).astype('float32')
utt.verify_grad(conv3d, [signals, filters], eps=1e-1, mode=mode) utt.verify_grad(conv3d, [signals, filters], eps=1e-1, mode=mode)
### Additional Test that covers the case of patched implementation for filter with Tf=1 # Additional Test that covers the case of patched implementation for filter with Tf=1
Ns, Ts, C, Hs, Ws = 3, 10, 3, 32, 32 Ns, Ts, C, Hs, Ws = 3, 10, 3, 32, 32
Nf, Tf, C, Hf, Wf = 32, 1 , 3, 5 , 5 Nf, Tf, C, Hf, Wf = 32, 1, 3, 5, 5
signals = numpy.arange(Ns*Ts*C*Hs*Ws).reshape(Ns, Ts, C, Hs, Ws).astype('float32') signals = numpy.arange(Ns * Ts * C * Hs * Ws).reshape(Ns, Ts, C, Hs, Ws).astype('float32')
filters = numpy.arange(Nf*Tf*C*Hf*Wf).reshape(Nf, Tf, C, Hf, Wf).astype('float32') filters = numpy.arange(Nf * Tf * C * Hf * Wf).reshape(Nf, Tf, C, Hf, Wf).astype('float32')
t0 = time.time() t0 = time.time()
pyres = pyconv3d(signals, filters) pyres = pyconv3d(signals, filters)
...@@ -143,7 +143,7 @@ def test_conv3d(mode=mode_without_gpu, shared=theano.tensor._shared): ...@@ -143,7 +143,7 @@ def test_conv3d(mode=mode_without_gpu, shared=theano.tensor._shared):
s_signals = shared(signals) s_signals = shared(signals)
s_filters = shared(filters) s_filters = shared(filters)
s_output = shared(signals*0) s_output = shared(signals * 0)
out = conv3d(s_signals, s_filters, out = conv3d(s_signals, s_filters,
signals_shape=signals.shape, signals_shape=signals.shape,
......
from __future__ import absolute_import, print_function, division from __future__ import absolute_import, print_function, division
from nose.plugins.skip import SkipTest
import numpy import numpy
import unittest import unittest
...@@ -22,13 +21,11 @@ class T_Images2Neibs(unittest_tools.InferShapeTester): ...@@ -22,13 +21,11 @@ class T_Images2Neibs(unittest_tools.InferShapeTester):
for shape, pshape in [((10, 7, 18, 18), (2, 2)), for shape, pshape in [((10, 7, 18, 18), (2, 2)),
((10, 7, 6, 18), (3, 2)), ((10, 7, 6, 18), (3, 2)),
((5, 7, 66, 66), (33, 33)), ((5, 7, 66, 66), (33, 33)),
((5, 7, 68, 66), (34, 33)) ((5, 7, 68, 66), (34, 33))]:
]:
for border in ['valid', 'ignore_borders']: for border in ['valid', 'ignore_borders']:
for dtype in self.dtypes: for dtype in self.dtypes:
images = shared( images = shared(
numpy.arange(numpy.prod(shape), dtype=dtype numpy.arange(numpy.prod(shape), dtype=dtype).reshape(shape))
).reshape(shape))
neib_shape = T.as_tensor_variable(pshape) neib_shape = T.as_tensor_variable(pshape)
f = function([], f = function([],
...@@ -51,8 +48,7 @@ class T_Images2Neibs(unittest_tools.InferShapeTester): ...@@ -51,8 +48,7 @@ class T_Images2Neibs(unittest_tools.InferShapeTester):
shape = (2, 3, 4, 4) shape = (2, 3, 4, 4)
for dtype in self.dtypes: for dtype in self.dtypes:
images = shared( images = shared(
numpy.arange(numpy.prod(shape), dtype=dtype numpy.arange(numpy.prod(shape), dtype=dtype).reshape(shape))
).reshape(shape))
neib_shape = T.as_tensor_variable((2, 2)) neib_shape = T.as_tensor_variable((2, 2))
for border in ['valid', 'ignore_borders']: for border in ['valid', 'ignore_borders']:
...@@ -64,10 +60,10 @@ class T_Images2Neibs(unittest_tools.InferShapeTester): ...@@ -64,10 +60,10 @@ class T_Images2Neibs(unittest_tools.InferShapeTester):
# print images.get_value(borrow=True) # print images.get_value(borrow=True)
neibs = f() neibs = f()
# print neibs # print neibs
assert numpy.allclose(neibs, assert numpy.allclose(neibs, [
[[ 0, 1, 4, 5], [0, 1, 4, 5],
[ 2, 3, 6, 7], [2, 3, 6, 7],
[ 8, 9, 12, 13], [8, 9, 12, 13],
[10, 11, 14, 15], [10, 11, 14, 15],
[16, 17, 20, 21], [16, 17, 20, 21],
[18, 19, 22, 23], [18, 19, 22, 23],
...@@ -111,23 +107,23 @@ class T_Images2Neibs(unittest_tools.InferShapeTester): ...@@ -111,23 +107,23 @@ class T_Images2Neibs(unittest_tools.InferShapeTester):
assert self.op in [type(node.op) assert self.op in [type(node.op)
for node in f.maker.fgraph.toposort()] for node in f.maker.fgraph.toposort()]
assert numpy.allclose(neibs, assert numpy.allclose(neibs, [
[[ 0, 1, 2, 5, 6, 7, 10, 11, 12], [0, 1, 2, 5, 6, 7, 10, 11, 12],
[ 2, 3, 4, 7, 8, 9, 12, 13, 14], [2, 3, 4, 7, 8, 9, 12, 13, 14],
[ 10, 11, 12, 15, 16, 17, 20, 21, 22], [10, 11, 12, 15, 16, 17, 20, 21, 22],
[ 12, 13, 14, 17, 18, 19, 22, 23, 24], [12, 13, 14, 17, 18, 19, 22, 23, 24],
[ 25, 26, 27, 30, 31, 32, 35, 36, 37], [25, 26, 27, 30, 31, 32, 35, 36, 37],
[ 27, 28, 29, 32, 33, 34, 37, 38, 39], [27, 28, 29, 32, 33, 34, 37, 38, 39],
[ 35, 36, 37, 40, 41, 42, 45, 46, 47], [35, 36, 37, 40, 41, 42, 45, 46, 47],
[ 37, 38, 39, 42, 43, 44, 47, 48, 49], [37, 38, 39, 42, 43, 44, 47, 48, 49],
[ 50, 51, 52, 55, 56, 57, 60, 61, 62], [50, 51, 52, 55, 56, 57, 60, 61, 62],
[ 52, 53, 54, 57, 58, 59, 62, 63, 64], [52, 53, 54, 57, 58, 59, 62, 63, 64],
[ 60, 61, 62, 65, 66, 67, 70, 71, 72], [60, 61, 62, 65, 66, 67, 70, 71, 72],
[ 62, 63, 64, 67, 68, 69, 72, 73, 74], [62, 63, 64, 67, 68, 69, 72, 73, 74],
[ 75, 76, 77, 80, 81, 82, 85, 86, 87], [75, 76, 77, 80, 81, 82, 85, 86, 87],
[ 77, 78, 79, 82, 83, 84, 87, 88, 89], [77, 78, 79, 82, 83, 84, 87, 88, 89],
[ 85, 86, 87, 90, 91, 92, 95, 96, 97], [85, 86, 87, 90, 91, 92, 95, 96, 97],
[ 87, 88, 89, 92, 93, 94, 97, 98, 99], [87, 88, 89, 92, 93, 94, 97, 98, 99],
[100, 101, 102, 105, 106, 107, 110, 111, 112], [100, 101, 102, 105, 106, 107, 110, 111, 112],
[102, 103, 104, 107, 108, 109, 112, 113, 114], [102, 103, 104, 107, 108, 109, 112, 113, 114],
[110, 111, 112, 115, 116, 117, 120, 121, 122], [110, 111, 112, 115, 116, 117, 120, 121, 122],
...@@ -142,7 +138,7 @@ class T_Images2Neibs(unittest_tools.InferShapeTester): ...@@ -142,7 +138,7 @@ class T_Images2Neibs(unittest_tools.InferShapeTester):
# mode=self.mode) # mode=self.mode)
# print g() # print g()
#assert numpy.allclose(images.get_value(borrow=True), g()) # assert numpy.allclose(images.get_value(borrow=True), g())
def test_neibs_bad_shape(self): def test_neibs_bad_shape(self):
shape = (2, 3, 10, 10) shape = (2, 3, 10, 10)
...@@ -171,28 +167,28 @@ class T_Images2Neibs(unittest_tools.InferShapeTester): ...@@ -171,28 +167,28 @@ class T_Images2Neibs(unittest_tools.InferShapeTester):
expected1 = [[24, 20, 21, 4, 0, 1, 9, 5, 6], expected1 = [[24, 20, 21, 4, 0, 1, 9, 5, 6],
[21, 22, 23, 1, 2, 3, 6, 7, 8], [21, 22, 23, 1, 2, 3, 6, 7, 8],
[23, 24, 20, 3, 4, 0, 8, 9, 5], [23, 24, 20, 3, 4, 0, 8, 9, 5],
[ 9, 5, 6, 14, 10, 11, 19, 15, 16], [9, 5, 6, 14, 10, 11, 19, 15, 16],
[ 6, 7, 8, 11, 12, 13, 16, 17, 18], [6, 7, 8, 11, 12, 13, 16, 17, 18],
[ 8, 9, 5, 13, 14, 10, 18, 19, 15], [8, 9, 5, 13, 14, 10, 18, 19, 15],
[19, 15, 16, 24, 20, 21, 4, 0, 1], [19, 15, 16, 24, 20, 21, 4, 0, 1],
[16, 17, 18, 21, 22, 23, 1, 2, 3], [16, 17, 18, 21, 22, 23, 1, 2, 3],
[18, 19, 15, 23, 24, 20, 3, 4, 0]] [18, 19, 15, 23, 24, 20, 3, 4, 0]]
expected2 = [[ 24, 20, 21, 4, 0, 1, 9, 5, 6], expected2 = [[24, 20, 21, 4, 0, 1, 9, 5, 6],
[ 22, 23, 24, 2, 3, 4, 7, 8, 9], [22, 23, 24, 2, 3, 4, 7, 8, 9],
[ 14, 10, 11, 19, 15, 16, 24, 20, 21], [14, 10, 11, 19, 15, 16, 24, 20, 21],
[ 12, 13, 14, 17, 18, 19, 22, 23, 24]] [12, 13, 14, 17, 18, 19, 22, 23, 24]]
expected3 = [[19, 15, 16, 24, 20, 21, 4, 0, 1, 9, 5, 6, 14, 10, 11], expected3 = [[19, 15, 16, 24, 20, 21, 4, 0, 1, 9, 5, 6, 14, 10, 11],
[17, 18, 19, 22, 23, 24, 2, 3, 4, 7, 8, 9, 12, 13, 14], [17, 18, 19, 22, 23, 24, 2, 3, 4, 7, 8, 9, 12, 13, 14],
[ 9, 5, 6, 14, 10, 11, 19, 15, 16, 24, 20, 21, 4, 0, 1], [9, 5, 6, 14, 10, 11, 19, 15, 16, 24, 20, 21, 4, 0, 1],
[ 7, 8, 9, 12, 13, 14, 17, 18, 19, 22, 23, 24, 2, 3, 4]] [7, 8, 9, 12, 13, 14, 17, 18, 19, 22, 23, 24, 2, 3, 4]]
expected4 = [[23, 24, 20, 21, 22, 3, 4, 0, 1, 2, 8, 9, 5, 6, 7], expected4 = [[23, 24, 20, 21, 22, 3, 4, 0, 1, 2, 8, 9, 5, 6, 7],
[21, 22, 23, 24, 20, 1, 2, 3, 4, 0, 6, 7, 8, 9, 5], [21, 22, 23, 24, 20, 1, 2, 3, 4, 0, 6, 7, 8, 9, 5],
[13, 14, 10, 11, 12, 18, 19, 15, 16, 17, 23, 24, 20, 21, 22], [13, 14, 10, 11, 12, 18, 19, 15, 16, 17, 23, 24, 20, 21, 22],
[11, 12, 13, 14, 10, 16, 17, 18, 19, 15, 21, 22, 23, 24, 20]] [11, 12, 13, 14, 10, 16, 17, 18, 19, 15, 21, 22, 23, 24, 20]]
expected5 = [[24, 20, 21, 4, 0, 1, 9, 5, 6], expected5 = [[24, 20, 21, 4, 0, 1, 9, 5, 6],
[22, 23, 24, 2, 3, 4, 7, 8, 9], [22, 23, 24, 2, 3, 4, 7, 8, 9],
[ 9, 5, 6, 14, 10, 11, 19, 15, 16], [9, 5, 6, 14, 10, 11, 19, 15, 16],
[ 7, 8, 9, 12, 13, 14, 17, 18, 19], [7, 8, 9, 12, 13, 14, 17, 18, 19],
[19, 15, 16, 24, 20, 21, 4, 0, 1], [19, 15, 16, 24, 20, 21, 4, 0, 1],
[17, 18, 19, 22, 23, 24, 2, 3, 4]] [17, 18, 19, 22, 23, 24, 2, 3, 4]]
expected6 = [[24, 20, 21, 4, 0, 1, 9, 5, 6], expected6 = [[24, 20, 21, 4, 0, 1, 9, 5, 6],
...@@ -212,8 +208,8 @@ class T_Images2Neibs(unittest_tools.InferShapeTester): ...@@ -212,8 +208,8 @@ class T_Images2Neibs(unittest_tools.InferShapeTester):
[(80, 90, 5, 5), (3, 3), (2, 3), expected5], [(80, 90, 5, 5), (3, 3), (2, 3), expected5],
[(1025, 9, 5, 5), (3, 3), (3, 2), expected6], [(1025, 9, 5, 5), (3, 3), (3, 2), expected6],
[(1, 1, 5, 1035), (3, 3), (3, 3), None], [(1, 1, 5, 1035), (3, 3), (3, 3), None],
[(1, 1, 1045, 5), (3, 3), (3, 3), None], [(1, 1, 1045, 5), (3, 3), (3, 3), None], ]
]): ):
for dtype in self.dtypes: for dtype in self.dtypes:
...@@ -231,16 +227,15 @@ class T_Images2Neibs(unittest_tools.InferShapeTester): ...@@ -231,16 +227,15 @@ class T_Images2Neibs(unittest_tools.InferShapeTester):
if expected.size > 1: if expected.size > 1:
for i in range(shape[0] * shape[1]): for i in range(shape[0] * shape[1]):
assert numpy.allclose( assert numpy.allclose(
neibs[i * expected.shape[0]: neibs[i * expected.shape[0]:(i + 1) * expected.shape[0], :],
(i + 1) * expected.shape[0], :],
expected + 25 * i), "wrap_centered" expected + 25 * i), "wrap_centered"
assert self.op in [type(node.op) assert self.op in [type(node.op)
for node in f.maker.fgraph.toposort()] for node in f.maker.fgraph.toposort()]
#g = function([], neibs2images(neibs, neib_shape, images.shape), mode=self.mode) # g = function([], neibs2images(neibs, neib_shape, images.shape), mode=self.mode)
# TODO: why this is commented? # TODO: why this is commented?
#assert numpy.allclose(images.get_value(borrow=True), g()) # assert numpy.allclose(images.get_value(borrow=True), g())
def test_neibs_bad_shape_wrap_centered(self): def test_neibs_bad_shape_wrap_centered(self):
shape = (2, 3, 10, 10) shape = (2, 3, 10, 10)
...@@ -309,7 +304,6 @@ class T_Images2Neibs(unittest_tools.InferShapeTester): ...@@ -309,7 +304,6 @@ class T_Images2Neibs(unittest_tools.InferShapeTester):
unittest_tools.verify_grad(fn, [images_val], mode=self.mode, unittest_tools.verify_grad(fn, [images_val], mode=self.mode,
eps=0.1) eps=0.1)
def test_grad_ignore_border(self): def test_grad_ignore_border(self):
shape = (2, 3, 5, 5) shape = (2, 3, 5, 5)
images_val = numpy.random.rand(*shape).astype('float32') images_val = numpy.random.rand(*shape).astype('float32')
...@@ -375,62 +369,41 @@ class T_Images2Neibs(unittest_tools.InferShapeTester): ...@@ -375,62 +369,41 @@ class T_Images2Neibs(unittest_tools.InferShapeTester):
shape = (100, 40, 6, 3) shape = (100, 40, 6, 3)
images = numpy.ones(shape).astype('float32') images = numpy.ones(shape).astype('float32')
x = T.ftensor4() x = T.ftensor4()
f = self._compile_and_check([x], self._compile_and_check(
[images2neibs( [x], [images2neibs(x, neib_shape=(2, 1), mode='valid')],
x, neib_shape=(2, 1), [images], Images2Neibs)
mode='valid')], self._compile_and_check(
[images], [x], [images2neibs(x, neib_shape=(2, 3), mode='valid')],
Images2Neibs [images], Images2Neibs)
)
f = self._compile_and_check([x],
[images2neibs(
x, neib_shape=(2, 3),
mode='valid')],
[images],
Images2Neibs
)
shape = (100, 40, 5, 4) shape = (100, 40, 5, 4)
images = numpy.ones(shape).astype('float32') images = numpy.ones(shape).astype('float32')
x = T.ftensor4() x = T.ftensor4()
f = self._compile_and_check([x], self._compile_and_check(
[images2neibs( [x], [images2neibs(
x, neib_shape=(2, 1), x, neib_shape=(2, 1), mode='ignore_borders')],
mode='ignore_borders')], [images], Images2Neibs)
[images],
Images2Neibs
)
shape = (100, 40, 5, 3) shape = (100, 40, 5, 3)
images = numpy.ones(shape).astype('float32') images = numpy.ones(shape).astype('float32')
x = T.ftensor4() x = T.ftensor4()
f = self._compile_and_check([x], self._compile_and_check(
[images2neibs( [x], [images2neibs(
x, neib_shape=(2, 3), x, neib_shape=(2, 3), mode='ignore_borders')],
mode='ignore_borders')], [images], Images2Neibs)
[images],
Images2Neibs
)
shape = (100, 40, 6, 7) shape = (100, 40, 6, 7)
images = numpy.ones(shape).astype('float32') images = numpy.ones(shape).astype('float32')
x = T.ftensor4() x = T.ftensor4()
f = self._compile_and_check([x], self._compile_and_check(
[images2neibs( [x], [images2neibs(
x, neib_shape=(2, 2), x, neib_shape=(2, 2), mode='ignore_borders')],
mode='ignore_borders')], [images], Images2Neibs)
[images],
Images2Neibs
)
shape = (100, 40, 5, 10) shape = (100, 40, 5, 10)
images = numpy.ones(shape).astype('float32') images = numpy.ones(shape).astype('float32')
x = T.ftensor4() x = T.ftensor4()
f = self._compile_and_check([x], self._compile_and_check(
[images2neibs( [x], [images2neibs(
x, neib_shape=(3, 3), x, neib_shape=(3, 3), mode='wrap_centered')],
mode='wrap_centered')], [images], Images2Neibs)
[images],
Images2Neibs
)
if __name__ == '__main__': if __name__ == '__main__':
unittest.main() unittest.main()
...@@ -25,7 +25,7 @@ from theano.tensor.nnet import (categorical_crossentropy, ...@@ -25,7 +25,7 @@ from theano.tensor.nnet import (categorical_crossentropy,
CrossentropyCategorical1HotGrad, CrossentropyCategorical1HotGrad,
sigmoid, softplus, Softmax, softmax, sigmoid, softplus, Softmax, softmax,
softmax_op, softmax_graph, SoftmaxWithBias, softmax_op, softmax_graph, SoftmaxWithBias,
softmax_with_bias, LogSoftmax, logsoftmax_op, softmax_with_bias, logsoftmax_op,
softmax_grad, SoftmaxGrad, softmax_grad, SoftmaxGrad,
Prepend_scalar_constant_to_each_row, Prepend_scalar_constant_to_each_row,
Prepend_scalar_to_each_row, Prepend_scalar_to_each_row,
...@@ -240,7 +240,7 @@ class T_LogSoftmax(utt.InferShapeTester): ...@@ -240,7 +240,7 @@ class T_LogSoftmax(utt.InferShapeTester):
# while in the log-softmax case they don't # while in the log-softmax case they don't
f3 = theano.function([x, y], [grad]) f3 = theano.function([x, y], [grad])
grad_ = f3(a, b) grad_ = f3(a, b)
assert numpy.all(numpy.isnan(grad_) == False) assert not numpy.any(numpy.isnan(grad_))
def test_isclose(self): def test_isclose(self):
def f(a): def f(a):
...@@ -372,7 +372,8 @@ class T_CrossentropySoftmax1HotWithBiasDx(utt.InferShapeTester): ...@@ -372,7 +372,8 @@ class T_CrossentropySoftmax1HotWithBiasDx(utt.InferShapeTester):
admat_val /= admat_val.sum(axis=1).reshape(10, 1) admat_val /= admat_val.sum(axis=1).reshape(10, 1)
advec_val = rng.rand(10).astype(config.floatX) advec_val = rng.rand(10).astype(config.floatX)
alvec_val = rng.randint(low=0, high=5, size=10) alvec_val = rng.randint(low=0, high=5, size=10)
self._compile_and_check([advec, admat, alvec], self._compile_and_check(
[advec, admat, alvec],
[CrossentropySoftmax1HotWithBiasDx()(advec, admat, alvec)], [CrossentropySoftmax1HotWithBiasDx()(advec, admat, alvec)],
[advec_val, admat_val, alvec_val], [advec_val, admat_val, alvec_val],
CrossentropySoftmax1HotWithBiasDx) CrossentropySoftmax1HotWithBiasDx)
...@@ -417,7 +418,8 @@ class T_CrossentropySoftmaxArgmax1HotWithBias(utt.InferShapeTester): ...@@ -417,7 +418,8 @@ class T_CrossentropySoftmaxArgmax1HotWithBias(utt.InferShapeTester):
def grad_on_softmax(x, b): def grad_on_softmax(x, b):
return self.op(x, b, y_idx=numpy.random.randint( return self.op(x, b, y_idx=numpy.random.randint(
low=0, high=n_classes, size=n_samples))[1] low=0, high=n_classes, size=n_samples))[1]
utt.verify_grad(grad_on_softmax, utt.verify_grad(
grad_on_softmax,
[numpy.random.rand(n_samples, n_classes), [numpy.random.rand(n_samples, n_classes),
numpy.random.rand(n_classes)]) numpy.random.rand(n_classes)])
...@@ -429,7 +431,8 @@ class T_CrossentropySoftmaxArgmax1HotWithBias(utt.InferShapeTester): ...@@ -429,7 +431,8 @@ class T_CrossentropySoftmaxArgmax1HotWithBias(utt.InferShapeTester):
admat_val = rng.rand(3, 5).astype(config.floatX) admat_val = rng.rand(3, 5).astype(config.floatX)
advec_val = rng.rand(5).astype(config.floatX) advec_val = rng.rand(5).astype(config.floatX)
alvec_val = rng.randint(low=0, high=5, size=3) alvec_val = rng.randint(low=0, high=5, size=3)
self._compile_and_check([admat, advec, alvec], self._compile_and_check(
[admat, advec, alvec],
CrossentropySoftmaxArgmax1HotWithBias()(admat, advec, alvec), CrossentropySoftmaxArgmax1HotWithBias()(admat, advec, alvec),
[admat_val, advec_val, alvec_val], [admat_val, advec_val, alvec_val],
CrossentropySoftmaxArgmax1HotWithBias) CrossentropySoftmaxArgmax1HotWithBias)
...@@ -475,12 +478,14 @@ class T_prepend(utt.InferShapeTester): ...@@ -475,12 +478,14 @@ class T_prepend(utt.InferShapeTester):
rng = numpy.random.RandomState(utt.fetch_seed()) rng = numpy.random.RandomState(utt.fetch_seed())
admat_val = rng.rand(3, 5).astype(config.floatX) admat_val = rng.rand(3, 5).astype(config.floatX)
adscal_val = numpy.asarray(rng.rand(), dtype=config.floatX).item() adscal_val = numpy.asarray(rng.rand(), dtype=config.floatX).item()
self._compile_and_check([admat], self._compile_and_check(
[admat],
[Prepend_scalar_constant_to_each_row(adscal_val)(admat)], [Prepend_scalar_constant_to_each_row(adscal_val)(admat)],
[admat_val], [admat_val],
Prepend_scalar_constant_to_each_row) Prepend_scalar_constant_to_each_row)
self._compile_and_check([adscal, admat], self._compile_and_check(
[adscal, admat],
[Prepend_scalar_to_each_row()(adscal, admat)], [Prepend_scalar_to_each_row()(adscal, admat)],
[adscal_val, admat_val], [adscal_val, admat_val],
Prepend_scalar_to_each_row) Prepend_scalar_to_each_row)
...@@ -496,7 +501,8 @@ class T_CrossentropyCategorical1HotGrad(utt.InferShapeTester): ...@@ -496,7 +501,8 @@ class T_CrossentropyCategorical1HotGrad(utt.InferShapeTester):
advec_val = rng.rand(3).astype(config.floatX) advec_val = rng.rand(3).astype(config.floatX)
admat_val = rng.rand(3, 2).astype(config.floatX) admat_val = rng.rand(3, 2).astype(config.floatX)
alvec_val = [0, 1, 0] alvec_val = [0, 1, 0]
self._compile_and_check([advec, admat, alvec], self._compile_and_check(
[advec, admat, alvec],
[CrossentropyCategorical1HotGrad()(advec, admat, alvec)], [CrossentropyCategorical1HotGrad()(advec, admat, alvec)],
[advec_val, admat_val, alvec_val], [advec_val, admat_val, alvec_val],
CrossentropyCategorical1HotGrad) CrossentropyCategorical1HotGrad)
...@@ -510,7 +516,8 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester): ...@@ -510,7 +516,8 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester):
op = crossentropy_categorical_1hot op = crossentropy_categorical_1hot
xe = op(x, one_of_n) xe = op(x, one_of_n)
f = theano.function([x, one_of_n], xe) f = theano.function([x, one_of_n], xe)
x_val = numpy.asarray([[.4, .6, .0], [.1, .8, .1]], x_val = numpy.asarray(
[[.4, .6, .0], [.1, .8, .1]],
dtype=config.floatX) dtype=config.floatX)
xe_val = f(x_val, [0, 1]) xe_val = f(x_val, [0, 1])
assert numpy.allclose(xe_val, -numpy.log([.4, .8])) assert numpy.allclose(xe_val, -numpy.log([.4, .8]))
...@@ -526,7 +533,8 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester): ...@@ -526,7 +533,8 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester):
rng = numpy.random.RandomState(utt.fetch_seed()) rng = numpy.random.RandomState(utt.fetch_seed())
admat_val = rng.rand(3, 2).astype(config.floatX) admat_val = rng.rand(3, 2).astype(config.floatX)
alvec_val = [0, 1, 0] alvec_val = [0, 1, 0]
self._compile_and_check([admat, alvec], self._compile_and_check(
[admat, alvec],
[CrossentropyCategorical1Hot()(admat, alvec)], [CrossentropyCategorical1Hot()(admat, alvec)],
[admat_val, alvec_val], [admat_val, alvec_val],
CrossentropyCategorical1Hot) CrossentropyCategorical1Hot)
...@@ -535,7 +543,7 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester): ...@@ -535,7 +543,7 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester):
x = tensor.matrix('x') x = tensor.matrix('x')
one_of_n = tensor.lvector('one_of_n') one_of_n = tensor.lvector('one_of_n')
op = crossentropy_categorical_1hot op = crossentropy_categorical_1hot
xe = op(x, one_of_n) # xe = op(x, one_of_n)
fgraph = gof.FunctionGraph( fgraph = gof.FunctionGraph(
[x, one_of_n], [x, one_of_n],
...@@ -569,7 +577,7 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester): ...@@ -569,7 +577,7 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester):
b = tensor.vector('b') b = tensor.vector('b')
one_of_n = tensor.lvector('one_of_n') one_of_n = tensor.lvector('one_of_n')
op = crossentropy_categorical_1hot op = crossentropy_categorical_1hot
xe = op(x, one_of_n) # xe = op(x, one_of_n)
fgraph = gof.FunctionGraph( fgraph = gof.FunctionGraph(
[x, b, one_of_n], [x, b, one_of_n],
...@@ -752,11 +760,11 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester): ...@@ -752,11 +760,11 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester):
# Basic case # Basic case
expressions = [ expressions = [
T.sum(-T.log(softmax(x)[T.arange(y.shape[0]), y])), T.sum(
-T.log(softmax(x)[T.arange(y.shape[0]), y])),
-T.sum(T.log(softmax(x)[T.arange(y.shape[0]), y])), -T.sum(T.log(softmax(x)[T.arange(y.shape[0]), y])),
-T.sum(T.log(softmax(x))[T.arange(y.shape[0]), y]), -T.sum(T.log(softmax(x))[T.arange(y.shape[0]), y]),
T.sum(-T.log(softmax(x))[T.arange(y.shape[0]), y]) T.sum(-T.log(softmax(x))[T.arange(y.shape[0]), y])]
]
for expr in expressions: for expr in expressions:
# Verify the optimizer worked on the expressions # Verify the optimizer worked on the expressions
f = theano.function([x, y], expr, mode=mode) f = theano.function([x, y], expr, mode=mode)
...@@ -867,7 +875,7 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester): ...@@ -867,7 +875,7 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester):
try: try:
ops = [node.op for node in g.maker.fgraph.toposort()] ops = [node.op for node in g.maker.fgraph.toposort()]
assert len(ops) == 5 assert len(ops) == 5
#there's an extra dimshuffle in there # there's an extra dimshuffle in there
# but I can't think of a good rule to get rid of it # but I can't think of a good rule to get rid of it
assert crossentropy_softmax_1hot_with_bias_dx in ops assert crossentropy_softmax_1hot_with_bias_dx in ops
assert softmax_op in ops assert softmax_op in ops
...@@ -931,8 +939,7 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester): ...@@ -931,8 +939,7 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester):
T.sum(-T.log(softmax(x)[T.arange(yi.shape[0]), yi])), T.sum(-T.log(softmax(x)[T.arange(yi.shape[0]), yi])),
-T.sum(T.log(softmax(x)[T.arange(yi.shape[0]), yi])), -T.sum(T.log(softmax(x)[T.arange(yi.shape[0]), yi])),
-T.sum(T.log(softmax(x))[T.arange(yi.shape[0]), yi]), -T.sum(T.log(softmax(x))[T.arange(yi.shape[0]), yi]),
T.sum(-T.log(softmax(x))[T.arange(yi.shape[0]), yi]) T.sum(-T.log(softmax(x))[T.arange(yi.shape[0]), yi])]
]
for expr in expressions: for expr in expressions:
# Verify the optimizer worked on the expressions # Verify the optimizer worked on the expressions
...@@ -1253,8 +1260,7 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester): ...@@ -1253,8 +1260,7 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester):
a * T.mean(-T.log(softmax(x))[T.arange(y.shape[0]), y]), a * T.mean(-T.log(softmax(x))[T.arange(y.shape[0]), y]),
-a * T.mean(T.log(softmax(x))[T.arange(y.shape[0]), y]), -a * T.mean(T.log(softmax(x))[T.arange(y.shape[0]), y]),
a * (-T.mean(T.log(softmax(x))[T.arange(y.shape[0]), y])), a * (-T.mean(T.log(softmax(x))[T.arange(y.shape[0]), y])),
a * T.mean(T.log(softmax(x))[T.arange(y.shape[0]), y]), a * T.mean(T.log(softmax(x))[T.arange(y.shape[0]), y]), ]
]
for expr in expressions: for expr in expressions:
# Verify the optimizer worked on the expressions # Verify the optimizer worked on the expressions
...@@ -1278,8 +1284,9 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester): ...@@ -1278,8 +1284,9 @@ class T_CrossentropyCategorical1Hot(utt.InferShapeTester):
raise raise
# Verify the gradient when providing output gradient # Verify the gradient when providing output gradient
h = theano.function([x, y, a], h = theano.function(
T.grad(expr, x, known_grads={expr: a * x.sum()}), mode=mode) [x, y, a], T.grad(expr, x, known_grads={expr: a * x.sum()}),
mode=mode)
try: try:
assert 6 <= len(h.maker.fgraph.toposort()) <= 8 assert 6 <= len(h.maker.fgraph.toposort()) <= 8
validate_grad_graph(h) validate_grad_graph(h)
...@@ -1319,6 +1326,7 @@ def test_argmax_pushdown(): ...@@ -1319,6 +1326,7 @@ def test_argmax_pushdown():
[x], [x],
[out]) [out])
assert hasattr(fgraph.outputs[0].tag, 'trace')
backup = config.warn.argmax_pushdown_bug backup = config.warn.argmax_pushdown_bug
config.warn.argmax_pushdown_bug = False config.warn.argmax_pushdown_bug = False
try: try:
...@@ -1514,14 +1522,14 @@ class Test_softmax_opt: ...@@ -1514,14 +1522,14 @@ class Test_softmax_opt:
p_y = T.exp(c) / T.exp(c).sum(axis=0) p_y = T.exp(c) / T.exp(c).sum(axis=0)
# test that function contains softmax and no div. # test that function contains softmax and no div.
f = theano.function([c], p_y) theano.function([c], p_y)
# printing.debugprint(f) # printing.debugprint(f)
# test that function contains softmax and no div. # test that function contains softmax and no div.
backup = config.warn.sum_div_dimshuffle_bug backup = config.warn.sum_div_dimshuffle_bug
config.warn.sum_div_dimshuffle_bug = False config.warn.sum_div_dimshuffle_bug = False
try: try:
g = theano.function([c], T.grad(p_y.sum(), c)) theano.function([c], T.grad(p_y.sum(), c))
finally: finally:
config.warn.sum_div_dimshuffle_bug = backup config.warn.sum_div_dimshuffle_bug = backup
# printing.debugprint(g) # printing.debugprint(g)
...@@ -1533,14 +1541,14 @@ class Test_softmax_opt: ...@@ -1533,14 +1541,14 @@ class Test_softmax_opt:
p_y = T.exp(c) / T.exp(c).sum() p_y = T.exp(c) / T.exp(c).sum()
# test that function contains softmax and no div. # test that function contains softmax and no div.
f = theano.function([c], p_y) theano.function([c], p_y)
# printing.debugprint(f) # printing.debugprint(f)
# test that function contains softmax and no div. # test that function contains softmax and no div.
backup = config.warn.sum_div_dimshuffle_bug backup = config.warn.sum_div_dimshuffle_bug
config.warn.sum_div_dimshuffle_bug = False config.warn.sum_div_dimshuffle_bug = False
try: try:
g = theano.function([c], T.grad(p_y.sum(), c)) theano.function([c], T.grad(p_y.sum(), c))
finally: finally:
config.warn.sum_div_dimshuffle_bug = backup config.warn.sum_div_dimshuffle_bug = backup
# printing.debugprint(g) # printing.debugprint(g)
...@@ -1614,7 +1622,6 @@ def test_relu(): ...@@ -1614,7 +1622,6 @@ def test_relu():
dtype=config.floatX) dtype=config.floatX)
y = relu(x, alpha).eval({x: X, alpha: A}) y = relu(x, alpha).eval({x: X, alpha: A})
assert numpy.allclose(y, numpy.where(X > 0, X, A * X), rtol=3e-5) assert numpy.allclose(y, numpy.where(X > 0, X, A * X), rtol=3e-5)
# test that for alpha of ndarray don't cause upcast. # test that for alpha of ndarray don't cause upcast.
x = matrix('x', dtype='float32') x = matrix('x', dtype='float32')
rng = numpy.random.RandomState(seed) rng = numpy.random.RandomState(seed)
...@@ -1733,7 +1740,7 @@ def test_binary_crossentropy_reshape(): ...@@ -1733,7 +1740,7 @@ def test_binary_crossentropy_reshape():
SoftsignTester = makeBroadcastTester( SoftsignTester = makeBroadcastTester(
op=softsign, op=softsign,
expected=upcast_int8_nfunc(lambda inputs: check_floatX( expected=upcast_int8_nfunc(lambda inputs: check_floatX(
inputs, inputs/(1.0+numpy.fabs(inputs)))), inputs, inputs / (1.0 + numpy.fabs(inputs)))),
good=_good_broadcast_unary_normal_float_no_complex, good=_good_broadcast_unary_normal_float_no_complex,
name='SoftsignTester', name='SoftsignTester',
) )
...@@ -16,7 +16,7 @@ from theano.tensor.nnet.sigm import ( ...@@ -16,7 +16,7 @@ from theano.tensor.nnet.sigm import (
compute_mul, is_1pexp, parse_mul_tree, perform_sigm_times_exp, compute_mul, is_1pexp, parse_mul_tree, perform_sigm_times_exp,
register_local_1msigmoid, simplify_mul, register_local_1msigmoid, simplify_mul,
) )
from theano.tensor.tests.test_basic import (makeBroadcastTester, rand, from theano.tensor.tests.test_basic import (makeBroadcastTester,
check_floatX, upcast_int8_nfunc, check_floatX, upcast_int8_nfunc,
_good_broadcast_unary_normal_no_complex) _good_broadcast_unary_normal_no_complex)
...@@ -45,7 +45,7 @@ UltraFastSigmoidTester = makeBroadcastTester( ...@@ -45,7 +45,7 @@ UltraFastSigmoidTester = makeBroadcastTester(
good=_good_broadcast_unary_normal_no_complex, good=_good_broadcast_unary_normal_no_complex,
# grad=_grad_broadcast_unary_normal, # grad=_grad_broadcast_unary_normal,
name='UltraFastSigmoidTester', name='UltraFastSigmoidTester',
# This is an approx of the sigmoid. That is why we raise eps # This is an approx of the sigmoid. That is why we raise eps
eps=5e-2) eps=5e-2)
HardSigmoidTester = makeBroadcastTester( HardSigmoidTester = makeBroadcastTester(
...@@ -55,7 +55,7 @@ HardSigmoidTester = makeBroadcastTester( ...@@ -55,7 +55,7 @@ HardSigmoidTester = makeBroadcastTester(
good=_good_broadcast_unary_normal_no_complex, good=_good_broadcast_unary_normal_no_complex,
# grad=_grad_broadcast_unary_normal, # grad=_grad_broadcast_unary_normal,
name='HardSigmoidTester', name='HardSigmoidTester',
# This is an approx of the sigmoid. That is why we raise eps # This is an approx of the sigmoid. That is why we raise eps
eps=1e-1) eps=1e-1)
...@@ -146,20 +146,20 @@ class T_sigmoid_opts(unittest.TestCase): ...@@ -146,20 +146,20 @@ class T_sigmoid_opts(unittest.TestCase):
# todo: solve issue #4589 first # todo: solve issue #4589 first
# assert check_stack_trace( # assert check_stack_trace(
# f, ops_to_check=[sigmoid, theano.tensor.inplace.neg_inplace]) # f, ops_to_check=[sigmoid, theano.tensor.inplace.neg_inplace])
assert [node.op for node in f.maker.fgraph.toposort()] == [sigmoid, assert ([node.op for node in f.maker.fgraph.toposort()] ==
theano.tensor.inplace.neg_inplace] [sigmoid, theano.tensor.inplace.neg_inplace])
f(data) f(data)
f = theano.function([x], T.fill(x, -1.0) / (1 - T.exp(-x)), mode=m) f = theano.function([x], T.fill(x, -1.0) / (1 - T.exp(-x)), mode=m)
assert [node.op for node in f.maker.fgraph.toposort()] != [sigmoid, assert ([node.op for node in f.maker.fgraph.toposort()] != [sigmoid,
theano.tensor.inplace.neg_inplace] theano.tensor.inplace.neg_inplace])
f(data) f(data)
f = theano.function([x], T.fill(x, -1.0) / (2 + T.exp(-x)), mode=m) f = theano.function([x], T.fill(x, -1.0) / (2 + T.exp(-x)), mode=m)
assert [node.op for node in f.maker.fgraph.toposort()] != [sigmoid, assert ([node.op for node in f.maker.fgraph.toposort()] != [sigmoid,
theano.tensor.inplace.neg_inplace] theano.tensor.inplace.neg_inplace])
f(data) f(data)
f = theano.function([x], T.fill(x, -1.1) / (1 + T.exp(-x)), mode=m) f = theano.function([x], T.fill(x, -1.1) / (1 + T.exp(-x)), mode=m)
assert [node.op for node in f.maker.fgraph.toposort()] != [sigmoid, assert ([node.op for node in f.maker.fgraph.toposort()] != [sigmoid,
theano.tensor.inplace.neg_inplace] theano.tensor.inplace.neg_inplace])
f(data) f(data)
# tests double inv_1_plus_exp with neg # tests double inv_1_plus_exp with neg
...@@ -170,33 +170,33 @@ class T_sigmoid_opts(unittest.TestCase): ...@@ -170,33 +170,33 @@ class T_sigmoid_opts(unittest.TestCase):
((1 + T.exp(x)) * (1 + T.exp(-x))), mode=m) ((1 + T.exp(x)) * (1 + T.exp(-x))), mode=m)
# todo: solve issue #4589 first # todo: solve issue #4589 first
# assert check_stack_trace(f, ops_to_check=[sigmoid, T.mul]) # assert check_stack_trace(f, ops_to_check=[sigmoid, T.mul])
assert [node.op for node in f.maker.fgraph.toposort()] == [sigmoid, assert ([node.op for node in f.maker.fgraph.toposort()] == [sigmoid,
T.mul] T.mul])
f(data) f(data)
f = theano.function([x], (T.fill(x, -1.1) * T.exp(x)) / f = theano.function([x], (T.fill(x, -1.1) * T.exp(x)) /
((1 + T.exp(x)) * (1 + T.exp(-x))), mode=m) ((1 + T.exp(x)) * (1 + T.exp(-x))), mode=m)
assert [node.op for node in f.maker.fgraph.toposort()] != [sigmoid, assert ([node.op for node in f.maker.fgraph.toposort()] != [sigmoid,
T.mul, theano.tensor.inplace.neg_inplace] T.mul, theano.tensor.inplace.neg_inplace])
f(data) f(data)
f = theano.function([x], (T.fill(x, -1.0) * T.exp(x)) / f = theano.function([x], (T.fill(x, -1.0) * T.exp(x)) /
((2 + T.exp(x)) * (1 + T.exp(-x))), mode=m) ((2 + T.exp(x)) * (1 + T.exp(-x))), mode=m)
assert [node.op for node in f.maker.fgraph.toposort()] != [sigmoid, assert ([node.op for node in f.maker.fgraph.toposort()] != [sigmoid,
T.mul, theano.tensor.inplace.neg_inplace] T.mul, theano.tensor.inplace.neg_inplace])
f(data) f(data)
f = theano.function([x], (T.fill(x, -1.0) * T.exp(x)) / f = theano.function([x], (T.fill(x, -1.0) * T.exp(x)) /
((1 + T.exp(x)) * (2 + T.exp(-x))), mode=m) ((1 + T.exp(x)) * (2 + T.exp(-x))), mode=m)
assert [node.op for node in f.maker.fgraph.toposort()] != [sigmoid, assert ([node.op for node in f.maker.fgraph.toposort()] != [sigmoid,
T.mul, theano.tensor.inplace.neg_inplace] T.mul, theano.tensor.inplace.neg_inplace])
f(data) f(data)
f = theano.function([x], (T.fill(x, -1.0) * T.exp(x)) / f = theano.function([x], (T.fill(x, -1.0) * T.exp(x)) /
((1 + T.exp(x)) * (1 + T.exp(x))), mode=m) ((1 + T.exp(x)) * (1 + T.exp(x))), mode=m)
assert [node.op for node in f.maker.fgraph.toposort()] != [sigmoid, assert ([node.op for node in f.maker.fgraph.toposort()] != [sigmoid,
T.mul, theano.tensor.inplace.neg_inplace] T.mul, theano.tensor.inplace.neg_inplace])
f(data) f(data)
f = theano.function([x], (T.fill(x, -1.0) * T.exp(x)) / f = theano.function([x], (T.fill(x, -1.0) * T.exp(x)) /
((1 + T.exp(x)) * (2 + T.exp(-x))), mode=m) ((1 + T.exp(x)) * (2 + T.exp(-x))), mode=m)
assert [node.op for node in f.maker.fgraph.toposort()] != [sigmoid, assert ([node.op for node in f.maker.fgraph.toposort()] != [sigmoid,
T.mul, theano.tensor.inplace.neg_inplace] T.mul, theano.tensor.inplace.neg_inplace])
f(data) f(data)
finally: finally:
...@@ -219,8 +219,8 @@ class T_sigmoid_opts(unittest.TestCase): ...@@ -219,8 +219,8 @@ class T_sigmoid_opts(unittest.TestCase):
# tests inv_1_plus_exp # tests inv_1_plus_exp
f = theano.function([x], 1 - T.fill(x, 1.0) / (1 + T.exp(-x)), mode=m) f = theano.function([x], 1 - T.fill(x, 1.0) / (1 + T.exp(-x)), mode=m)
assert check_stack_trace(f, ops_to_check=[tensor.neg, sigmoid_inplace]) assert check_stack_trace(f, ops_to_check=[tensor.neg, sigmoid_inplace])
assert [node.op for node in f.maker.fgraph.toposort()] == [tensor.neg, assert ([node.op for node in f.maker.fgraph.toposort()] == [tensor.neg,
sigmoid_inplace] sigmoid_inplace])
def test_local_sigm_times_exp(self): def test_local_sigm_times_exp(self):
""" """
...@@ -249,8 +249,7 @@ class T_sigmoid_opts(unittest.TestCase): ...@@ -249,8 +249,7 @@ class T_sigmoid_opts(unittest.TestCase):
f = theano.function( f = theano.function(
[x, y], [x, y],
(sigmoid(x) * sigmoid(-y) * -tensor.exp(-x) * (sigmoid(x) * sigmoid(-y) * -tensor.exp(-x) *
tensor.exp(x * y) * tensor.exp(y)), tensor.exp(x * y) * tensor.exp(y)), mode=m)
mode=m)
match(f, [sigmoid, tensor.mul, tensor.neg, tensor.exp, sigmoid, match(f, [sigmoid, tensor.mul, tensor.neg, tensor.exp, sigmoid,
tensor.mul]) tensor.mul])
# assert check_stack_trace(f, ops_to_check=[sigmoid, tensor.mul, # assert check_stack_trace(f, ops_to_check=[sigmoid, tensor.mul,
...@@ -286,11 +285,11 @@ class T_sigmoid_opts(unittest.TestCase): ...@@ -286,11 +285,11 @@ class T_sigmoid_opts(unittest.TestCase):
-x * sigmoid(-x) * (y * (-1 * z))) -x * sigmoid(-x) * (y * (-1 * z)))
ok(-sigmoid(-x) * ok(-sigmoid(-x) *
(exp(y) * (-exp(-z) * 3 * -exp(x)) * (exp(y) * (-exp(-z) * 3 * -exp(x)) *
(y * 2 * (-sigmoid(-y) * (z + t) * exp(z)) * sigmoid(z))) * (y * 2 * (-sigmoid(-y) * (z + t) * exp(z)) * sigmoid(z))) * -
-sigmoid(x), sigmoid(x),
sigmoid(x) * sigmoid(x) *
(-sigmoid(y) * (-sigmoid(-z) * 3) * (y * 2 * ((z + t) * exp(z)))) * (-sigmoid(y) * (-sigmoid(-z) * 3) * (y * 2 * ((z + t) * exp(z)))) *
-sigmoid(x)) (-sigmoid(x)))
ok(exp(-x) * -exp(-x) * (-sigmoid(x) * -sigmoid(x)), ok(exp(-x) * -exp(-x) * (-sigmoid(x) * -sigmoid(x)),
-sigmoid(-x) * sigmoid(-x)) -sigmoid(-x) * sigmoid(-x))
ok(-exp(x) * -sigmoid(-x) * -exp(-x), ok(-exp(x) * -sigmoid(-x) * -exp(-x),
...@@ -333,7 +332,7 @@ class T_sigmoid_opts(unittest.TestCase): ...@@ -333,7 +332,7 @@ class T_sigmoid_opts(unittest.TestCase):
topo = f.maker.fgraph.toposort() topo = f.maker.fgraph.toposort()
assert topo[0].op == ultra_fast_sigmoid assert topo[0].op == ultra_fast_sigmoid
assert len(topo) == 1 assert len(topo) == 1
ux_v = f([[-50, -10, -4, -1, 0, 1, 4, 10, 50]]) f([[-50, -10, -4, -1, 0, 1, 4, 10, 50]])
def test_local_hard_sigmoid(self): def test_local_hard_sigmoid(self):
x = tensor.matrix('x') x = tensor.matrix('x')
...@@ -350,7 +349,7 @@ class T_sigmoid_opts(unittest.TestCase): ...@@ -350,7 +349,7 @@ class T_sigmoid_opts(unittest.TestCase):
f = theano.function([x], s, mode=mode) f = theano.function([x], s, mode=mode)
topo = f.maker.fgraph.toposort() topo = f.maker.fgraph.toposort()
assert not any([n.op == sigmoid for n in topo]) assert not any([n.op == sigmoid for n in topo])
ux_v = f([[-50, -10, -4, -1, 0, 1, 4, 10, 50]]) f([[-50, -10, -4, -1, 0, 1, 4, 10, 50]])
mode2 = mode.excluding('fusion').excluding('inplace') mode2 = mode.excluding('fusion').excluding('inplace')
f2 = theano.function([x], s, mode=mode2) f2 = theano.function([x], s, mode=mode2)
...@@ -416,7 +415,7 @@ class T_softplus_opts(unittest.TestCase): ...@@ -416,7 +415,7 @@ class T_softplus_opts(unittest.TestCase):
out = T.log(1 - sigmoid(x).reshape([x.size])) out = T.log(1 - sigmoid(x).reshape([x.size]))
f = theano.function([x], out, mode=self.m) f = theano.function([x], out, mode=self.m)
topo = f.maker.fgraph.toposort() topo = f.maker.fgraph.toposort()
#assert len(topo) == 3 # assert len(topo) == 3
assert any(isinstance(node.op, T.Reshape) for node in topo) assert any(isinstance(node.op, T.Reshape) for node in topo)
assert any(isinstance(getattr(node.op, 'scalar_op', None), assert any(isinstance(getattr(node.op, 'scalar_op', None),
theano.tensor.nnet.sigm.ScalarSoftplus) theano.tensor.nnet.sigm.ScalarSoftplus)
......
...@@ -72,14 +72,6 @@ whitelist_flake8 = [ ...@@ -72,14 +72,6 @@ whitelist_flake8 = [
"tensor/tests/test_blas_scipy.py", "tensor/tests/test_blas_scipy.py",
"tensor/tests/test_mpi.py", "tensor/tests/test_mpi.py",
"tensor/nnet/__init__.py", "tensor/nnet/__init__.py",
"tensor/nnet/tests/__init__.py",
"tensor/nnet/tests/test_conv.py",
"tensor/nnet/tests/test_neighbours.py",
"tensor/nnet/tests/test_nnet.py",
"tensor/nnet/tests/test_conv3d2d.py",
"tensor/nnet/tests/test_conv3d.py",
"tensor/nnet/tests/speed_test_conv.py",
"tensor/nnet/tests/test_sigm.py",
"tensor/signal/__init__.py", "tensor/signal/__init__.py",
"tensor/signal/tests/__init__.py", "tensor/signal/tests/__init__.py",
"scalar/__init__.py", "scalar/__init__.py",
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论