Input Vector and ensemble

Last question has a lot going here, I divided then into small ones to conquer.

I try to have one 4x1 input vector connected with one ensemble (‘pre’) which is 4x1, in which each neural is fed one elements from the input vector. However, in GUI there are only one single slide for the input. The detail of the input says the fanout is 4, meaning there are four synaptic connection respectively to the four neurons in the ‘pre’ ensemble,but why there is only one slide to control the input instead of four ?

The codes are :

import nengo
import numpy as np
import matplotlib.pyplot as plt

model = nengo.Network()
Amat = np.array([[1,2,3,4]]) #define an array of four elements

print('Amat size:',Amat.size) #size is total elements amount

radius = 1
model = nengo.Network(label='Matrix Multiplication', seed=123)
with model:
    # Make 1 Ensemble to be fed with input
    pre = nengo.Ensemble(4, dimensions=1, radius=2)  #4x1 dimension, matching the input
    inputA = nengo.Node(Amat.size)
    nengo.Connection(inputA, pre)
    post = nengo.Ensemble(1, dimensions=1)  # post ensemble has only one neuron.
    conn = nengo.Connection(pre, post, solver=nengo.solvers.LstsqL2(weights=True))
    conn.learning_rule_type = nengo.Oja(learning_rate=6e-8)  #Oja learning method 

Then, I have tried alternative way by using a ensembleArray which is has one block of 4 elements, still have the input vector which is defined from 4x1 array. At this time happy to see the slider has four control item seem that the input vector is indeed 4x1 as expected. But the connection between the 4x1 pre and 1x1 post report error. How the learning rule of Oja in last section can be applied as well ? I notice the difference between two ways for defining the input vector is whether using ravel() or .size to define length of the array, wasn’t the same from either one? The new code are :

model = nengo.Network()
Amat = np.array([[1],[2],[3],[4]])
Bmat = np.array([1])
print('size of Amat:',Amat.size)
model = nengo.Network(label='2x2 Oja', seed=123)
with model:
    source = nengo.Node(Amat.ravel())
    pre = nengo.networks.EnsembleArray(1, Amat.size, radius=1)
    post = nengo.networks.EnsembleArray(1, Bmat.size, radius=1)
    nengo.Connection(source, pre.input)
    conn = nengo.Connection(pre.output, post.input)

Hi @selleo, I edited your post to fix the code formatting, hope you don’t mind! For future reference, code should have three backticks (```) on a separate line before and after the code block to render like code (see your edited post for a concrete example).

The reason that your second example gives an error is that pre.output has dimensionality 4 (since Amat.size is 4), and you’re trying to connect to an input with dimensionality 1 (since Bmat.size is 1).

From your description, it sounds to me like you’re treating ensembles and ensemble arrays as matrices where connections do something like matrix multiplication – going from a 4x1 pre to 1x1 post makes sense if you’re doing matrix multiplication. However, in Nengo we think of ensembles and ensemble arrays as vectors. So you’re going from a 4-dimensional pre to a 1-dimensional post, which is underspecified. Do you want to pass all of your 4 dimensions to the 1-dimensional post? Just one of them? We require you to be explicit. So here are a few ways to do it:

  1. Connect the first dimensions of pre to post wtih
    conn = nengo.Connection(pre.output[0], post.input).
  2. Connect all of the dimensions of pre to post with
    conn = nengo.Connection(pre.output, post.input, transform=[[1, 1, 1, 1]]).
    Note that this will naturally sum all of the dimensions of pre in post. This may or may not be what you want.

If you want to compute some kind of function between the connection of pre and post, then you likely don’t want to split them up into separate ensemble arrays, and instead keep them as one ensemble.

For learning, we need to make direct ensemble-to-ensemble connections. pre.output and post.input are both Nodes that redirect information to the appropriate ensemble. However, for learning, we need to deal with neurons directly.

I believe that rather than using ensemble arrays, you might be better off assigning a dimension to each of your neurons. So perhaps something like this model:

import nengo
import numpy as np

Amat = np.array([1, 2, 3, 4])

radius = 1
with nengo.Network() as model:
    # Make 1 Ensemble to be fed with input
    pre = nengo.Ensemble(4, dimensions=4, radius=2)
    inputA = nengo.Node(Amat)
    nengo.Connection(inputA, pre)
    post = nengo.Ensemble(1, dimensions=1)
    conn = nengo.Connection(
        pre, post, transform=[[1, 1, 1, 1]],
        solver=nengo.solvers.LstsqL2(weights=True))
    conn.learning_rule_type = nengo.Oja(learning_rate=6e-8)

I’ve assumed that you want all neurons in pre connected to post with weight 1, but you could change these values through changing the transform.

Hope this helps!

Thanks for the patient ! @tbekolay
As you said, actually my attemp was rather concerning matrices multiplication, rather than transform from high dimensions to low dimensions.Actually the first part code I posted are more close to what I wanna achieve with Nengo, though I have doubt about the input.

Let me rephrase it a bit:

Assume there are four pre neurons are weighted connect to one post neuron, their dimensions are 1. The scenario can be treated as each pre neuron transfer their value which is grey color to the post neuron. As you said, Nengo assumes the dimension of ensemble could be 2 or 3, saying RGB in color case, but I just have each pre neuron transfer one single value (essentially is equal to vector of dimensionality is 1)

Then each weighted connection will be updated by proportional product of its input (from pre) and output from post. I believe this is exactly Oja rule is implemented by Nengo. Hower the problems is, if I define ensemble as 4x1, how I connect a four-elements array to the pre-ensemble such that each element is fed to one neuron in the pre ensemble?

So far from the tutorial examples of Nengo it seem that input always feed same value to different neurons in an ensemble. This is making sense with Nengo indeed, however not with the real applications. i.e, 1 from input array to first neuron, 2 from input array to the second neuron from the 4x1 pre-ensemble, instead of fetch one pixel and feed it to all 4 neurons. So how to achieve this ?

A post was split to a new topic: What is meant by direct mode?

I feel like there’s a bit of a language barrier and a gap of understanding happening here that is hard to overcome using textual communication. Is it possible to set-up a Google hangouts to discuss what you are attempting and why?