def test_circularconv_helpers(): """Test the circular convolution helper functions in Numpy""" rng = np.random.RandomState(43232) dims = 1000 invert_a = True invert_b = False x = rng.randn(dims) y = rng.randn(dims) z0 = circconv(x, y, invert_a=invert_a, invert_b=invert_b) dims2 = 2 * dims - (2 if dims % 2 == 0 else 1) inA = nengo.networks.CircularConvolution._input_transform( dims, first=True, invert=invert_a) inB = nengo.networks.CircularConvolution._input_transform( dims, first=False, invert=invert_b) outC = nengo.networks.CircularConvolution._output_transform(dims) XY = np.zeros((dims2, 2)) XY += np.dot(inA.reshape(dims2, 2, dims), x) XY += np.dot(inB.reshape(dims2, 2, dims), y) C = XY[:, 0] * XY[:, 1] z1 = np.dot(outC, C) assert np.allclose(z0, z1)
def test_helpers(self): """Test the circular convolution helper functions in Numpy""" rng = np.random.RandomState(43232) dims = 1000 invert_a = True invert_b = False x = rng.randn(dims) y = rng.randn(dims) z0 = circconv(x, y, invert_a=invert_a, invert_b=invert_b) dims2 = 2 * dims - (2 if dims % 2 == 0 else 1) inA = CircularConvolution._input_transform(dims, first=True, invert=invert_a) inB = CircularConvolution._input_transform(dims, first=False, invert=invert_b) outC = CircularConvolution._output_transform(dims) XY = np.zeros((dims2, 2)) XY += np.dot(inA.reshape(dims2, 2, dims), x) XY += np.dot(inB.reshape(dims2, 2, dims), y) C = XY[:, 0] * XY[:, 1] z1 = np.dot(outC, C) assert_allclose(self, logger, z0, z1)
def test_circularconv_transforms(invert_a, invert_b): """Test the circular convolution transforms""" rng = np.random.RandomState(43232) dims = 100 x = rng.randn(dims) y = rng.randn(dims) z0 = circconv(x, y, invert_a=invert_a, invert_b=invert_b) cconv = nengo.networks.CircularConvolution(nengo.Direct(), dims, invert_a=invert_a, invert_b=invert_b) XY = np.dot(cconv.transformA, x) * np.dot(cconv.transformB, y) z1 = np.dot(cconv.transform_out, XY) assert np.allclose(z0, z1)
def test_circularconv_transforms(invert_a, invert_b, rng): """Test the circular convolution transforms""" dims = 100 x = rng.randn(dims) y = rng.randn(dims) z0 = circconv(x, y, invert_a=invert_a, invert_b=invert_b) tr_a = transform_in(dims, 'A', invert_a) tr_b = transform_in(dims, 'B', invert_b) tr_out = transform_out(dims) XY = np.dot(tr_a, x) * np.dot(tr_b, y) z1 = np.dot(tr_out, XY) assert np.allclose(z0, z1)
def test_circularconv_transforms(invert_a, invert_b, rng): """Test the circular convolution transforms""" dims = 100 x = rng.randn(dims) y = rng.randn(dims) z0 = circconv(x, y, invert_a=invert_a, invert_b=invert_b) tr_a = transform_in(dims, 'A', invert_a) tr_b = transform_in(dims, 'B', invert_b) tr_out = transform_out(dims) XY = np.dot(tr_a, x) * np.dot(tr_b, y) z1 = np.dot(tr_out, XY) assert np.allclose(z0, z1)
def test_circularconv_transforms(invert_a, invert_b): """Test the circular convolution transforms""" rng = np.random.RandomState(43232) dims = 100 x = rng.randn(dims) y = rng.randn(dims) z0 = circconv(x, y, invert_a=invert_a, invert_b=invert_b) cconv = nengo.networks.CircularConvolution( 1, dims, invert_a=invert_a, invert_b=invert_b) XY = np.dot(cconv.transformA, x) * np.dot(cconv.transformB, y) z1 = np.dot(cconv.transform_out, XY) assert np.allclose(z0, z1)
def test_neural_accuracy(Simulator, seed, rng, dims, neurons_per_product=128): a = rng.normal(scale=np.sqrt(1.0 / dims), size=dims) b = rng.normal(scale=np.sqrt(1.0 / dims), size=dims) result = circconv(a, b) model = nengo.Network(label="circular conv", seed=seed) model.config[nengo.Ensemble].neuron_type = nengo.LIFRate() with model: input_a = nengo.Node(a) input_b = nengo.Node(b) cconv = nengo.networks.CircularConvolution(neurons_per_product, dimensions=dims) nengo.Connection(input_a, cconv.input_a, synapse=None) nengo.Connection(input_b, cconv.input_b, synapse=None) res_p = nengo.Probe(cconv.output) with Simulator(model) as sim: sim.run(0.01) error = rms(result - sim.data[res_p][-1]) assert error < 0.1
def test_neural_accuracy(Simulator, seed, rng, dims, neurons_per_product=128): a = rng.normal(scale=np.sqrt(1./dims), size=dims) b = rng.normal(scale=np.sqrt(1./dims), size=dims) result = circconv(a, b) model = nengo.Network(label="circular conv", seed=seed) model.config[nengo.Ensemble].neuron_type = nengo.LIFRate() with model: inputA = nengo.Node(a) inputB = nengo.Node(b) cconv = nengo.networks.CircularConvolution( neurons_per_product, dimensions=dims) nengo.Connection(inputA, cconv.A, synapse=None) nengo.Connection(inputB, cconv.B, synapse=None) res_p = nengo.Probe(cconv.output) sim = Simulator(model) sim.run(0.01) error = rmse(result, sim.data[res_p][-1]) assert error < 0.1
def test_input_magnitude(Simulator, dims=16, magnitude=10): """Test to make sure the magnitude scaling works. Builds two different CircularConvolution networks, one with the correct magnitude and one with 1.0 as the input_magnitude. """ rng = np.random.RandomState(4238) neurons_per_product = 128 a = rng.normal(scale=np.sqrt(1./dims), size=dims) * magnitude b = rng.normal(scale=np.sqrt(1./dims), size=dims) * magnitude result = circconv(a, b) model = nengo.Network(label="circular conv", seed=1) model.config[nengo.Ensemble].neuron_type = nengo.LIFRate() with model: inputA = nengo.Node(a) inputB = nengo.Node(b) cconv = nengo.networks.CircularConvolution( neurons_per_product, dimensions=dims, input_magnitude=magnitude) nengo.Connection(inputA, cconv.A, synapse=None) nengo.Connection(inputB, cconv.B, synapse=None) res_p = nengo.Probe(cconv.output) cconv_bad = nengo.networks.CircularConvolution( neurons_per_product, dimensions=dims, input_magnitude=1) # incorrect magnitude nengo.Connection(inputA, cconv_bad.A, synapse=None) nengo.Connection(inputB, cconv_bad.B, synapse=None) res_p_bad = nengo.Probe(cconv_bad.output) sim = Simulator(model) sim.run(0.01) error = rmse(result, sim.data[res_p][-1]) / (magnitude ** 2) error_bad = rmse(result, sim.data[res_p_bad][-1]) / (magnitude ** 2) assert error < 0.1 assert error_bad > 0.1
def test_input_magnitude(Simulator, seed, rng, dims=16, magnitude=10): """Test to make sure the magnitude scaling works. Builds two different CircularConvolution networks, one with the correct magnitude and one with 1.0 as the input_magnitude. """ neurons_per_product = 128 a = rng.normal(scale=np.sqrt(1. / dims), size=dims) * magnitude b = rng.normal(scale=np.sqrt(1. / dims), size=dims) * magnitude result = circconv(a, b) model = nengo.Network(label="circular conv", seed=seed) model.config[nengo.Ensemble].neuron_type = nengo.LIFRate() with model: inputA = nengo.Node(a) inputB = nengo.Node(b) cconv = nengo.networks.CircularConvolution(neurons_per_product, dimensions=dims, input_magnitude=magnitude) nengo.Connection(inputA, cconv.A, synapse=None) nengo.Connection(inputB, cconv.B, synapse=None) res_p = nengo.Probe(cconv.output) cconv_bad = nengo.networks.CircularConvolution( neurons_per_product, dimensions=dims, input_magnitude=1) # incorrect magnitude nengo.Connection(inputA, cconv_bad.A, synapse=None) nengo.Connection(inputB, cconv_bad.B, synapse=None) res_p_bad = nengo.Probe(cconv_bad.output) sim = Simulator(model) sim.run(0.01) error = rmse(result, sim.data[res_p][-1]) / (magnitude**2) error_bad = rmse(result, sim.data[res_p_bad][-1]) / (magnitude**2) assert error < 0.1 assert error_bad > 0.1
dims = map(int, sys.argv[2].split(",")) # neurons_per_product = 128 neurons_per_product = 256 simtime = 1.0 radius = 1 records = [] for i, dim in enumerate(dims): rng = np.random.RandomState(123) a = rng.normal(scale=np.sqrt(1.0 / dim), size=dim) b = rng.normal(scale=np.sqrt(1.0 / dim), size=dim) c = circconv(a, b) # --- Model with nengo.Network(seed=9) as model: inputA = nengo.Node(a) inputB = nengo.Node(b) A = nengo.networks.EnsembleArray(neurons_per_product, dim, radius=radius) B = nengo.networks.EnsembleArray(neurons_per_product, dim, radius=radius) C = nengo.networks.EnsembleArray(neurons_per_product, dim, radius=radius) D = nengo.networks.CircularConvolution(neurons_per_product,
dims = map(int, sys.argv[2].split(',')) # neurons_per_product = 128 neurons_per_product = 256 simtime = 1.0 radius = 1 records = [] for i, dim in enumerate(dims): rng = np.random.RandomState(123) a = rng.normal(scale=np.sqrt(1./dim), size=dim) b = rng.normal(scale=np.sqrt(1./dim), size=dim) c = circconv(a, b) # --- Model with nengo.Network(seed=9) as model: inputA = nengo.Node(a) inputB = nengo.Node(b) A = nengo.networks.EnsembleArray( neurons_per_product, dim, radius=radius) B = nengo.networks.EnsembleArray( neurons_per_product, dim, radius=radius) C = nengo.networks.EnsembleArray( neurons_per_product, dim, radius=radius) D = nengo.networks.CircularConvolution( neurons_per_product, dim, input_magnitude=radius) nengo.Connection(inputA, A.input, synapse=None)
def test_circularconv(Simulator, nl, dims=4, neurons_per_product=128): rng = np.random.RandomState(42342) n_neurons = neurons_per_product n_neurons_d = 2 * neurons_per_product radius = 1 a = rng.normal(scale=np.sqrt(1./dims), size=dims) b = rng.normal(scale=np.sqrt(1./dims), size=dims) c = circconv(a, b) assert np.abs(a).max() < radius assert np.abs(b).max() < radius assert np.abs(c).max() < radius ### model model = nengo.Model("circular convolution") inputA = nengo.Node(output=a) inputB = nengo.Node(output=b) A = EnsembleArray(nl(n_neurons), dims, radius=radius) B = EnsembleArray(nl(n_neurons), dims, radius=radius) C = EnsembleArray(nl(n_neurons), dims, radius=radius) D = nengo.networks.CircularConvolution( neurons=nl(n_neurons_d), dimensions=A.dimensions, radius=radius) nengo.Connection(inputA, A.input) nengo.Connection(inputB, B.input) nengo.Connection(A.output, D.A) nengo.Connection(B.output, D.B) nengo.Connection(D.output, C.input) A_p = nengo.Probe(A.output, 'output', filter=0.03) B_p = nengo.Probe(B.output, 'output', filter=0.03) C_p = nengo.Probe(C.output, 'output', filter=0.03) D_p = nengo.Probe(D.ensemble.output, 'output', filter=0.03) # check FFT magnitude d = np.dot(D.transformA, a) + np.dot(D.transformB, b) assert np.abs(d).max() < radius ### simulation sim = Simulator(model) sim.run(1.0) t = sim.trange() with Plotter(Simulator, nl) as plt: def plot(sim, a, A, title=""): a_ref = np.tile(a, (len(t), 1)) a_sim = sim.data(A_p) colors = ['b', 'g', 'r', 'c', 'm', 'y'] for i in range(min(dims, len(colors))): plt.plot(t, a_ref[:, i], '--', color=colors[i]) plt.plot(t, a_sim[:, i], '-', color=colors[i]) plt.title(title) plt.subplot(221) plot(sim, a, A, title="A") plt.subplot(222) plot(sim, b, B, title="B") plt.subplot(223) plot(sim, c, C, title="C") plt.subplot(224) plot(sim, d, D.ensemble, title="D") plt.savefig('test_circularconv.test_circularconv_%d.pdf' % dims) plt.close() ### results tmask = t > (0.5 + sim.model.dt/2) assert sim.data(A_p)[tmask].shape == (499, dims) a_sim = sim.data(A_p)[tmask].mean(axis=0) b_sim = sim.data(B_p)[tmask].mean(axis=0) c_sim = sim.data(C_p)[tmask].mean(axis=0) d_sim = sim.data(D_p)[tmask].mean(axis=0) rtol, atol = 0.1, 0.05 assert np.allclose(a, a_sim, rtol=rtol, atol=atol) assert np.allclose(b, b_sim, rtol=rtol, atol=atol) assert np.allclose(d, d_sim, rtol=rtol, atol=atol) assert rmse(c, c_sim) < 0.075
def test_circularconv(Simulator, nl, dims=4, neurons_per_product=128): rng = np.random.RandomState(4238) n_neurons = neurons_per_product n_neurons_d = 2 * neurons_per_product radius = 1 a = rng.normal(scale=np.sqrt(1./dims), size=dims) b = rng.normal(scale=np.sqrt(1./dims), size=dims) result = circconv(a, b) assert np.abs(a).max() < radius assert np.abs(b).max() < radius assert np.abs(result).max() < radius # --- model model = nengo.Network(label="circular convolution") with model: model.config[nengo.Ensemble].neuron_type = nl() inputA = nengo.Node(a) inputB = nengo.Node(b) A = EnsembleArray(n_neurons, dims, radius=radius) B = EnsembleArray(n_neurons, dims, radius=radius) cconv = nengo.networks.CircularConvolution( n_neurons_d, dimensions=dims) res = EnsembleArray(n_neurons, dims, radius=radius) nengo.Connection(inputA, A.input) nengo.Connection(inputB, B.input) nengo.Connection(A.output, cconv.A) nengo.Connection(B.output, cconv.B) nengo.Connection(cconv.output, res.input) A_p = nengo.Probe(A.output, synapse=0.03) B_p = nengo.Probe(B.output, synapse=0.03) res_p = nengo.Probe(res.output, synapse=0.03) # --- simulation sim = Simulator(model) sim.run(1.0) t = sim.trange() with Plotter(Simulator, nl) as plt: def plot(actual, probe, title=""): ref_y = np.tile(actual, (len(t), 1)) sim_y = sim.data[probe] colors = ['b', 'g', 'r', 'c', 'm', 'y'] for i in range(min(dims, len(colors))): plt.plot(t, ref_y[:, i], '--', color=colors[i]) plt.plot(t, sim_y[:, i], '-', color=colors[i]) plt.title(title) plt.subplot(311) plot(a, A_p, title="A") plt.subplot(312) plot(b, B_p, title="B") plt.subplot(313) plot(result, res_p, title="Result") plt.tight_layout() plt.savefig('test_circularconv.test_circularconv_%d.pdf' % dims) plt.close() # --- results tmask = t > (0.5 + sim.dt/2) assert sim.data[A_p][tmask].shape == (499, dims) a_sim = sim.data[A_p][tmask].mean(axis=0) b_sim = sim.data[B_p][tmask].mean(axis=0) res_sim = sim.data[res_p][tmask].mean(axis=0) rtol, atol = 0.1, 0.05 assert np.allclose(a, a_sim, rtol=rtol, atol=atol) assert np.allclose(b, b_sim, rtol=rtol, atol=atol) assert rmse(result, res_sim) < 0.075
def test_circconv_split(): dims = 16 seed = 1 npd = 100 sim_time = 0.1 rng = np.random.RandomState(seed) magnitude = 1.0 pstc = 0.005 a = rng.normal(scale=np.sqrt(1./dims), size=dims) * magnitude b = rng.normal(scale=np.sqrt(1./dims), size=dims) * magnitude result = circconv(a, b) model = nengo.Network(label="CircConv", seed=seed) model.config[nengo.Ensemble].neuron_type = nengo.LIFRate() with model: inputA = nengo.Node(a) inputB = nengo.Node(b) input_ea_a = nengo.networks.EnsembleArray( npd, dims, radius=np.sqrt(1./dims), label="A") input_ea_b = nengo.networks.EnsembleArray( npd, dims, radius=np.sqrt(1./dims), label="B") nengo.Connection(inputA, input_ea_a.input, synapse=None) nengo.Connection(inputB, input_ea_b.input, synapse=None) cconv = nengo.networks.CircularConvolution( npd, dimensions=dims, input_magnitude=magnitude) nengo.Connection(input_ea_a.output, cconv.A, synapse=pstc) nengo.Connection(input_ea_b.output, cconv.B, synapse=pstc) output = nengo.networks.EnsembleArray( npd, dims, radius=np.sqrt(1./dims), label="output") nengo.Connection(cconv.output, output.input, synapse=pstc) p = nengo.Probe(output.output) sim_no_split = nengo.Simulator(model) sim_no_split.run(sim_time) splitter = EnsembleArraySplitter() splitter.split(model, max_neurons=npd, preserve_zero_conns=False) assert len(model.networks) == 4 assert len(model.all_networks) == 7 assert len(model.ensembles) == 0 assert len(model.all_ensembles) == 3 * dims + 2 * (2 * dims + 4) sim_split = nengo.Simulator(model) sim_split.run(sim_time) pre_split_data = sim_no_split.data post_split_data = splitter.unsplit_data(sim_split) error = rmse(result, pre_split_data[p][-1]) assert error < 0.1 error = rmse(result, post_split_data[p][-1]) assert error < 0.1 error = rmse(pre_split_data[p][-1], post_split_data[p][-1]) assert error < 0.1 remove_log_file(splitter)
def test_circularconv(Simulator, nl, dims=4, neurons_per_product=128): rng = np.random.RandomState(4238) n_neurons = neurons_per_product n_neurons_d = 2 * neurons_per_product radius = 1 a = rng.normal(scale=np.sqrt(1.0 / dims), size=dims) b = rng.normal(scale=np.sqrt(1.0 / dims), size=dims) result = circconv(a, b) assert np.abs(a).max() < radius assert np.abs(b).max() < radius assert np.abs(result).max() < radius # --- model model = nengo.Network(label="circular convolution") with model: inputA = nengo.Node(output=a) inputB = nengo.Node(output=b) A = EnsembleArray(nl(n_neurons), dims, radius=radius) B = EnsembleArray(nl(n_neurons), dims, radius=radius) cconv = nengo.networks.CircularConvolution(neurons=nl(n_neurons_d), dimensions=dims) res = EnsembleArray(nl(n_neurons), dims, radius=radius) nengo.Connection(inputA, A.input) nengo.Connection(inputB, B.input) nengo.Connection(A.output, cconv.A) nengo.Connection(B.output, cconv.B) nengo.Connection(cconv.output, res.input) A_p = nengo.Probe(A.output, synapse=0.03) B_p = nengo.Probe(B.output, synapse=0.03) res_p = nengo.Probe(res.output, synapse=0.03) # --- simulation sim = Simulator(model) sim.run(1.0) t = sim.trange() with Plotter(Simulator, nl) as plt: def plot(actual, probe, title=""): ref_y = np.tile(actual, (len(t), 1)) sim_y = sim.data[probe] colors = ["b", "g", "r", "c", "m", "y"] for i in range(min(dims, len(colors))): plt.plot(t, ref_y[:, i], "--", color=colors[i]) plt.plot(t, sim_y[:, i], "-", color=colors[i]) plt.title(title) plt.subplot(311) plot(a, A_p, title="A") plt.subplot(312) plot(b, B_p, title="B") plt.subplot(313) plot(result, res_p, title="Result") plt.tight_layout() plt.savefig("test_circularconv.test_circularconv_%d.pdf" % dims) plt.close() # --- results tmask = t > (0.5 + sim.dt / 2) assert sim.data[A_p][tmask].shape == (499, dims) a_sim = sim.data[A_p][tmask].mean(axis=0) b_sim = sim.data[B_p][tmask].mean(axis=0) res_sim = sim.data[res_p][tmask].mean(axis=0) rtol, atol = 0.1, 0.05 assert np.allclose(a, a_sim, rtol=rtol, atol=atol) assert np.allclose(b, b_sim, rtol=rtol, atol=atol) assert rmse(result, res_sim) < 0.075
def _test_circularconv(self, dims=5, neurons_per_product=128): rng = np.random.RandomState(42342) n_neurons = neurons_per_product * dims n_neurons_d = 2 * neurons_per_product * (2 * dims - (2 if dims % 2 == 0 else 1)) radius = 1 a = rng.normal(scale=np.sqrt(1. / dims), size=dims) b = rng.normal(scale=np.sqrt(1. / dims), size=dims) c = circconv(a, b) self.assertTrue(np.abs(a).max() < radius) self.assertTrue(np.abs(b).max() < radius) self.assertTrue(np.abs(c).max() < radius) ### model model = nengo.Model("circular convolution") inputA = model.make_node("inputA", output=a) inputB = model.make_node("inputB", output=b) A = model.add( EnsembleArray('A', nengo.LIF(n_neurons), dims, radius=radius)) B = model.add( EnsembleArray('B', nengo.LIF(n_neurons), dims, radius=radius)) C = model.add( EnsembleArray('C', nengo.LIF(n_neurons), dims, radius=radius)) D = model.add( CircularConvolution('D', neurons=nengo.LIF(n_neurons_d), dimensions=A.dimensions, radius=radius)) inputA.connect_to(A) inputB.connect_to(B) A.connect_to(D.A) B.connect_to(D.B) D.output.connect_to(C) model.probe(A, filter=0.03) model.probe(B, filter=0.03) model.probe(C, filter=0.03) model.probe(D.ensemble, filter=0.03) # check FFT magnitude d = np.dot(D.transformA, a) + np.dot(D.transformB, b) self.assertTrue(np.abs(d).max() < radius) ### simulation sim = model.simulator(sim_class=self.Simulator) sim.run(1.0) t = sim.data(model.t).flatten() with Plotter(self.Simulator) as plt: def plot(sim, a, A, title=""): a_ref = np.tile(a, (len(t), 1)) a_sim = sim.data(A) colors = ['b', 'g', 'r', 'c', 'm', 'y'] for i in xrange(min(dims, len(colors))): plt.plot(t, a_ref[:, i], '--', color=colors[i]) plt.plot(t, a_sim[:, i], '-', color=colors[i]) plt.title(title) plt.subplot(221) plot(sim, a, A, title="A") plt.subplot(222) plot(sim, b, B, title="B") plt.subplot(223) plot(sim, c, C, title="C") plt.subplot(224) plot(sim, d, D.ensemble, title="D") plt.savefig('test_circularconv.test_circularconv_%d.pdf' % dims) plt.close() ### results tmask = t > (0.5 + sim.model.dt / 2) self.assertEqual(sim.data(A)[tmask].shape, (499, dims)) a_sim = sim.data(A)[tmask].mean(axis=0) b_sim = sim.data(B)[tmask].mean(axis=0) c_sim = sim.data(C)[tmask].mean(axis=0) d_sim = sim.data(D.ensemble)[tmask].mean(axis=0) rtol, atol = 0.1, 0.05 self.assertTrue(np.allclose(a, a_sim, rtol=rtol, atol=atol)) self.assertTrue(np.allclose(b, b_sim, rtol=rtol, atol=atol)) self.assertTrue(np.allclose(d, d_sim, rtol=rtol, atol=atol)) self.assertTrue(rmse(c, c_sim) < 0.075)
def _test_circularconv(self, dims=5, neurons_per_product=128): rng = np.random.RandomState(42342) n_neurons = neurons_per_product * dims n_neurons_d = 2 * neurons_per_product * ( 2*dims - (2 if dims % 2 == 0 else 1)) radius = 1 a = rng.normal(scale=np.sqrt(1./dims), size=dims) b = rng.normal(scale=np.sqrt(1./dims), size=dims) c = circconv(a, b) self.assertTrue(np.abs(a).max() < radius) self.assertTrue(np.abs(b).max() < radius) self.assertTrue(np.abs(c).max() < radius) ### model model = nengo.Model("circular convolution") inputA = model.make_node("inputA", output=a) inputB = model.make_node("inputB", output=b) A = model.add(EnsembleArray( 'A', nengo.LIF(n_neurons), dims, radius=radius)) B = model.add(EnsembleArray( 'B', nengo.LIF(n_neurons), dims, radius=radius)) C = model.add(EnsembleArray( 'C', nengo.LIF(n_neurons), dims, radius=radius)) D = model.add(CircularConvolution( 'D', neurons=nengo.LIF(n_neurons_d), dimensions=A.dimensions, radius=radius)) inputA.connect_to(A) inputB.connect_to(B) A.connect_to(D.A) B.connect_to(D.B) D.output.connect_to(C) model.probe(A, filter=0.03) model.probe(B, filter=0.03) model.probe(C, filter=0.03) model.probe(D.ensemble, filter=0.03) # check FFT magnitude d = np.dot(D.transformA, a) + np.dot(D.transformB, b) self.assertTrue(np.abs(d).max() < radius) ### simulation sim = model.simulator(sim_class=self.Simulator) sim.run(1.0) t = sim.data(model.t).flatten() with Plotter(self.Simulator) as plt: def plot(sim, a, A, title=""): a_ref = np.tile(a, (len(t), 1)) a_sim = sim.data(A) colors = ['b', 'g', 'r', 'c', 'm', 'y'] for i in xrange(min(dims, len(colors))): plt.plot(t, a_ref[:,i], '--', color=colors[i]) plt.plot(t, a_sim[:,i], '-', color=colors[i]) plt.title(title) plt.subplot(221) plot(sim, a, A, title="A") plt.subplot(222) plot(sim, b, B, title="B") plt.subplot(223) plot(sim, c, C, title="C") plt.subplot(224) plot(sim, d, D.ensemble, title="D") plt.savefig('test_circularconv.test_circularconv_%d.pdf' % dims) plt.close() ### results tmask = t > (0.5 + sim.model.dt/2) self.assertEqual(sim.data(A)[tmask].shape, (499, dims)) a_sim = sim.data(A)[tmask].mean(axis=0) b_sim = sim.data(B)[tmask].mean(axis=0) c_sim = sim.data(C)[tmask].mean(axis=0) d_sim = sim.data(D.ensemble)[tmask].mean(axis=0) rtol, atol = 0.1, 0.05 self.assertTrue(np.allclose(a, a_sim, rtol=rtol, atol=atol)) self.assertTrue(np.allclose(b, b_sim, rtol=rtol, atol=atol)) self.assertTrue(np.allclose(d, d_sim, rtol=rtol, atol=atol)) self.assertTrue(rmse(c, c_sim) < 0.075)