コード例 #1
0
ファイル: connections_test.py プロジェクト: EricSB/nupic.core
  def test_computeActivity_thresholded(self):
    for (name, cells, inputs, activeInputs,
         initialPermanence, connectedPermanence,
         expected) in (("Accepted",
                        [1, 2, 3], [42, 43, 44],
                        [42, 44], 0.55, 0.5,
                        [2, 2, 2]),
                       ("Rejected",
                        [1, 2, 3], [42, 43, 44],
                        [42, 44], 0.55, 0.6,
                        [0, 0, 0]),
                       ("No segments",
                        [], [42, 43, 44],
                        [42, 44], 0.55, 0.5,
                        []),
                       ("No active inputs",
                        [1, 2, 3], [42, 43, 44],
                        [], 0.55, 0.5,
                        [0, 0, 0])
         ):

      connections = SparseMatrixConnections(2048, 2048)
      segments = connections.createSegments(cells)
      connections.growSynapses(segments, inputs, initialPermanence)

      overlaps = connections.computeActivity(activeInputs, connectedPermanence)
      np.testing.assert_equal(overlaps[segments], expected, name)
コード例 #2
0
ファイル: connections_test.py プロジェクト: EricSB/nupic.core
  def test_computeActivity(self):
    for (name, cells, inputs, activeInputs,
         initialPermanence,
         expected) in (("Basic test",
                        [1, 2, 3], [42, 43, 44],
                        [42, 44], 0.45,
                        [2, 2, 2]),
                       ("Small permanence",
                        [1, 2, 3], [42, 43, 44],
                        [42, 44], 0.01,
                        [2, 2, 2]),
                       ("No segments",
                        [], [42, 43, 44],
                        [42, 44], 0.45,
                        []),
                       ("No active inputs",
                        [1, 2, 3], [42, 43, 44],
                        [], 0.45,
                        [0, 0, 0])
         ):

      connections = SparseMatrixConnections(2048, 2048)
      segments = connections.createSegments(cells)
      connections.growSynapses(segments, inputs, initialPermanence)

      overlaps = connections.computeActivity(activeInputs)
      np.testing.assert_equal(overlaps[segments], expected, name)
コード例 #3
0
ファイル: connections_test.py プロジェクト: EricSB/nupic.core
  def test_growSynapses(self):
    for (name,
         cells, growingSegments,
         presynapticInputs, activeInputs,
         initialPermanence, connectedPermanence,
         expected) in (("Basic test",
                        [1, 2, 3], [0, 2],
                        [42, 43, 44], [42, 43],
                        0.55, 0.5,
                        [2, 0, 2]),
                       ("No segments selected",
                        [1, 2, 3], [],
                        [42, 43, 44], [42, 43],
                        0.55, 0.5,
                        [0, 0, 0]),
                       ("No inputs selected",
                        [1, 2, 3], [0, 2],
                        [], [42, 43],
                        0.55, 0.5,
                        [0, 0, 0])
         ):

      connections = SparseMatrixConnections(2048, 2048)

      segments = connections.createSegments(cells)

      connections.growSynapses(segments[growingSegments], presynapticInputs,
                               initialPermanence)

      overlaps = connections.computeActivity(activeInputs, connectedPermanence)

      np.testing.assert_equal(overlaps[segments], expected, name)
コード例 #4
0
ファイル: connections_test.py プロジェクト: EricSB/nupic.core
  def test_mapSegmentsToSynapseCounts(self):
    connections = SparseMatrixConnections(2048, 2048)

    segments = connections.createSegments([1, 2, 3])
    connections.growSynapses(segments, [42, 43, 44], 0.5)
    np.testing.assert_equal(connections.mapSegmentsToSynapseCounts(segments),
                            [3, 3, 3])

    segments2 = connections.createSegments([4, 5])
    np.testing.assert_equal(connections.mapSegmentsToSynapseCounts(segments2),
                            [0, 0])

    np.testing.assert_equal(connections.mapSegmentsToSynapseCounts([]),
                            [])
コード例 #5
0
ファイル: connections_test.py プロジェクト: EricSB/nupic.core
  def test_adjustSynapses(self):
    for (name, cells, inputs,
         adjustedSegments, activeInputs,
         initialPermanence, activeDelta, inactiveDelta, connectedPermanence,
         expected) in (("Basic test",
                        [1, 2, 3], [42, 43, 44],
                        [0, 2], [42, 44],
                        0.45, 0.1, -0.1, 0.5,
                        [2, 0, 2]),
                       ("Reward inactive",
                        [1, 2, 3], [42, 43, 44],
                        [0, 2], [42, 44],
                        0.45, -0.1, 0.1, 0.5,
                        [1, 0, 1]),
                       ("No segments",
                        [1, 2, 3], [42, 43, 44],
                        [], [42, 44],
                        0.45, 0.1, -0.1, 0.5,
                        [0, 0, 0]),
                       ("No active synapses",
                        [1, 2, 3], [42, 43, 44],
                        [0, 2], [],
                        0.45, 0.1, -0.1, 0.5,
                        [0, 0, 0]),
                       ("Delta of zero",
                        [1, 2, 3], [42, 43, 44],
                        [0, 2], [42, 44],
                        0.55, 0.0, 0.0, 0.5,
                        [3, 3, 3])
         ):

      connections = SparseMatrixConnections(2048, 2048)

      segments = connections.createSegments(cells)

      connections.growSynapses(segments, inputs, initialPermanence)
      connections.adjustSynapses(segments[adjustedSegments],
                                 activeInputs, activeDelta, inactiveDelta)

      overlaps = connections.computeActivity(inputs, connectedPermanence)

      np.testing.assert_equal(overlaps[segments], expected, name)
コード例 #6
0
ファイル: connections_test.py プロジェクト: EricSB/nupic.core
  def test_whenPermanenceFallsBelowZero(self):
    connections = SparseMatrixConnections(2048, 2048)

    segments = connections.createSegments([1, 2, 3])

    connections.growSynapses(segments, [42, 43], 0.05)
    connections.adjustSynapses(segments, [42, 43], -0.06, 0.0)
    np.testing.assert_equal(connections.mapSegmentsToSynapseCounts(segments),
                            [0, 0, 0])

    connections.growSynapses(segments, [42, 43], 0.05)
    connections.adjustSynapses(segments, [], 0.0, -0.06)
    np.testing.assert_equal(connections.mapSegmentsToSynapseCounts(segments),
                            [0, 0, 0])

    connections.growSynapses(segments, [42, 43], 0.05)
    connections.adjustActiveSynapses(segments, [42, 43], -0.06)
    np.testing.assert_equal(connections.mapSegmentsToSynapseCounts(segments),
                            [0, 0, 0])

    connections.growSynapses(segments, [42, 43], 0.05)
    connections.adjustInactiveSynapses(segments, [], -0.06)
    np.testing.assert_equal(connections.mapSegmentsToSynapseCounts(segments),
                            [0, 0, 0])
コード例 #7
0
ファイル: connections_test.py プロジェクト: EricSB/nupic.core
  def test_clipPermanences(self):
    connections = SparseMatrixConnections(2048, 2048)

    # Destroy synapses with permanences <= 0.0
    segments = connections.createSegments([1, 2, 3])
    connections.growSynapses(segments, [42, 43, 44], 0.05)
    connections.growSynapses(segments, [45, 46], 0.1)
    connections.adjustInactiveSynapses(segments, [], -0.1)
    connections.clipPermanences(segments)
    np.testing.assert_equal(connections.mapSegmentsToSynapseCounts(segments),
                            [0, 0, 0])

    # Clip permanences to 1.0
    connections.growSynapses(segments, [42, 43, 44], 0.95)
    connections.adjustInactiveSynapses(segments, [], 0.50)
    connections.clipPermanences(segments)
    np.testing.assert_equal(connections.mapSegmentsToSynapseCounts(segments),
                            [3, 3, 3])
    connections.adjustInactiveSynapses(segments, [], -0.5)
    overlaps1 = connections.computeActivity([42, 43, 44], 0.49)
    overlaps2 = connections.computeActivity([42, 43, 44], 0.51)
    np.testing.assert_equal(overlaps1, [3, 3, 3])
    np.testing.assert_equal(overlaps2, [0, 0, 0])
コード例 #8
0
    def test_growSynapsesToSample_multi(self):

        rng = Random()

        for (name, cells, growingSegments, initialConnectedInputs,
             presynapticInputs, activeInputs, initialPermanence,
             connectedPermanence, sampleSizes,
             expected) in (("Basic test", [1, 2, 3], [0,
                                                      2], [], [42, 43, 44, 45],
                            [42, 43, 44, 45], 0.55, 0.5, [2, 3], [2, 0, 3]),
                           ("One already connected", [1, 2, 3], [0, 2], [42],
                            [42, 43, 44, 45], [42, 43, 44,
                                               45], 0.55, 0.5, [1,
                                                                2], [2, 0, 3]),
                           ("Higher sample size than axon count", [1, 2,
                                                                   3], [0, 2],
                            [], [42, 43, 44,
                                 45], [42, 43, 44,
                                       45], 0.55, 0.5, [5, 10], [4, 0, 4]),
                           ("Higher sample size than available axon count",
                            [1, 2, 3], [0, 2], [42, 43], [42, 43, 44, 45],
                            [42, 43, 44, 45], 0.55, 0.5, [3, 3], [4, 0, 4])):

            connections = SparseMatrixConnections(2048, 2048)

            segments = connections.createSegments(cells)

            connections.growSynapses(segments[growingSegments],
                                     initialConnectedInputs, initialPermanence)

            connections.growSynapsesToSample(segments[growingSegments],
                                             presynapticInputs, sampleSizes,
                                             initialPermanence, rng)

            overlaps = connections.computeActivity(activeInputs,
                                                   connectedPermanence)

            np.testing.assert_equal(overlaps[segments], expected, name)

        for (name, cells, growingSegments, initialConnectedInputs,
             presynapticInputs, activeInputs, initialPermanence,
             connectedPermanence,
             sampleSizes) in (("Basic randomness test", [1, 2, 3], [0, 2], [],
                               [42, 43, 44, 45], [42, 43], 0.55, 0.5, [2,
                                                                       3]), ):

            # Activate a subset of the inputs. The resulting overlaps should
            # differ on various trials.

            firstResult = None
            differingResults = False

            for _ in range(20):
                connections = SparseMatrixConnections(2048, 2048)

                segments = connections.createSegments(cells)

                connections.growSynapses(segments[growingSegments],
                                         initialConnectedInputs,
                                         initialPermanence)

                connections.growSynapsesToSample(segments[growingSegments],
                                                 presynapticInputs,
                                                 sampleSizes,
                                                 initialPermanence, rng)

                overlaps = connections.computeActivity(activeInputs,
                                                       connectedPermanence)

                if firstResult is None:
                    firstResult = overlaps[segments]
                else:
                    differingResults = not np.array_equal(
                        overlaps[segments], firstResult)
                    if differingResults:
                        break

            self.assertTrue(differingResults, name)
コード例 #9
0
ファイル: connections_test.py プロジェクト: EricSB/nupic.core
  def test_growSynapsesToSample_multi(self):

    rng = Random()

    for (name,
         cells, growingSegments,
         initialConnectedInputs, presynapticInputs, activeInputs,
         initialPermanence, connectedPermanence, sampleSizes,
         expected) in (("Basic test",
                        [1, 2, 3], [0, 2],
                        [], [42, 43, 44, 45],
                        [42, 43, 44, 45], 0.55, 0.5,
                        [2, 3],
                        [2, 0, 3]),
                       ("One already connected",
                        [1, 2, 3], [0, 2],
                        [42], [42, 43, 44, 45],
                        [42, 43, 44, 45], 0.55, 0.5,
                        [1, 2],
                        [2, 0, 3]),
                       ("Higher sample size than axon count",
                        [1, 2, 3], [0, 2],
                        [], [42, 43, 44, 45],
                        [42, 43, 44, 45], 0.55, 0.5,
                        [5, 10],
                        [4, 0, 4]),
                       ("Higher sample size than available axon count",
                        [1, 2, 3], [0, 2],
                        [42, 43], [42, 43, 44, 45],
                        [42, 43, 44, 45], 0.55, 0.5,
                        [3, 3],
                        [4, 0, 4])
                       ):

      connections = SparseMatrixConnections(2048, 2048)

      segments = connections.createSegments(cells)

      connections.growSynapses(
        segments[growingSegments], initialConnectedInputs, initialPermanence)

      connections.growSynapsesToSample(
        segments[growingSegments], presynapticInputs,
        sampleSizes, initialPermanence, rng)

      overlaps = connections.computeActivity(activeInputs, connectedPermanence)

      np.testing.assert_equal(overlaps[segments], expected, name)


    for (name,
         cells, growingSegments,
         initialConnectedInputs, presynapticInputs, activeInputs,
         initialPermanence, connectedPermanence,
         sampleSizes) in (("Basic randomness test",
                           [1, 2, 3], [0, 2],
                           [], [42, 43, 44, 45],
                           [42, 43], 0.55, 0.5, [2, 3]),
         ):

      # Activate a subset of the inputs. The resulting overlaps should
      # differ on various trials.

      firstResult = None
      differingResults = False

      for _ in xrange(20):
        connections = SparseMatrixConnections(2048, 2048)

        segments = connections.createSegments(cells)

        connections.growSynapses(
          segments[growingSegments], initialConnectedInputs, initialPermanence)

        connections.growSynapsesToSample(
          segments[growingSegments], presynapticInputs,
          sampleSizes, initialPermanence, rng)

        overlaps = connections.computeActivity(activeInputs,
                                               connectedPermanence)

        if firstResult is None:
          firstResult = overlaps[segments]
        else:
          differingResults = not np.array_equal(overlaps[segments], firstResult)
          if differingResults:
            break

      self.assertTrue(differingResults, name)
コード例 #10
0
class Thalamus(object):
  """

  A simple discrete time thalamus.  This thalamus has a 2D TRN layer and a 2D
  relay cell layer. L6 cells project to the dendrites of TRN cells - these
  connections are learned. TRN cells project to the dendrites of relay cells in
  a fixed fan-out pattern. A 2D feed forward input source projects to the relay
  cells in a fixed fan-out pattern.

  The output of the thalamus is the activity of each relay cell. This activity
  can be in one of three states: inactive, active (tonic), and active (burst).

  TRN cells control whether the relay cells will burst. If any dendrite on a TRN
  cell recognizes the current L6 pattern, it de-inactivates the T-type CA2+
  channels on the dendrites of any relay cell it projects to. These relay cells
  are then in "burst-ready mode".

  Feed forward activity is in the form of a binary vector corresponding to
  active/spiking axons (e.g. from ganglion cells). Any relay cells that receive
  input from an axon will either output tonic or burst activity depending on the
  state of the T-type CA2+ channels on their dendrites. Relay cells that don't
  receive input will remain inactive, regardless of their dendritic state.

  Usage:

    1. Train the TRN cells on a bunch of L6 patterns: learnL6Pattern()

    2. De-inactivate relay cells by sending in an L6 pattern: deInactivateCells()

    3. Compute feed forward activity for an input: computeFeedForwardActivity()

    4. reset()

    5. Goto 2

  """

  def __init__(self,
               trnCellShape=(32, 32),
               relayCellShape=(32, 32),
               inputShape=(32, 32),
               l6CellCount=1024,
               trnThreshold=10,
               relayThreshold=1,
               seed=42):
    """

    :param trnCellShape:
      a 2D shape for the TRN

    :param relayCellShape:
      a 2D shape for the relay cells

    :param l6CellCount:
      number of L6 cells

    :param trnThreshold:
      dendritic threshold for TRN cells. This is the min number of active L6
      cells on a dendrite for the TRN cell to recognize a pattern on that
      dendrite.

    :param relayThreshold:
      dendritic threshold for relay cells. This is the min number of active TRN
      cells on a dendrite for the relay cell to recognize a pattern on that
      dendrite.

    :param seed:
        Seed for the random number generator.
    """

    self.trnCellShape = trnCellShape
    self.trnWidth = trnCellShape[0]
    self.trnHeight = trnCellShape[1]
    self.relayCellShape = relayCellShape
    self.relayWidth = relayCellShape[0]
    self.relayHeight = relayCellShape[1]
    self.l6CellCount = l6CellCount
    self.trnThreshold = trnThreshold
    self.relayThreshold = relayThreshold
    self.inputShape = inputShape
    self.seed = seed
    self.rng = Random(seed)
    self.trnActivationThreshold = 5

    self.trnConnections = SparseMatrixConnections(
      trnCellShape[0]*trnCellShape[1], l6CellCount)

    self.relayConnections = SparseMatrixConnections(
      relayCellShape[0]*relayCellShape[1],
      trnCellShape[0]*trnCellShape[1])

    # Initialize/reset variables that are updated with calls to compute
    self.reset()

    self._initializeTRNToRelayCellConnections()


  def learnL6Pattern(self, l6Pattern, cellsToLearnOn):
    """
    Learn the given l6Pattern on TRN cell dendrites. The TRN cells to learn
    are given in cellsTeLearnOn. Each of these cells will learn this pattern on
    a single dendritic segment.

    :param l6Pattern:
      An SDR from L6. List of indices corresponding to L6 cells.

    :param cellsToLearnOn:
      Each cell index is (x,y) corresponding to the TRN cells that should learn
      this pattern. For each cell, create a new dendrite that stores this
      pattern. The SDR is stored on this dendrite


    """
    cellIndices = [self.trnCellIndex(x) for x in cellsToLearnOn]
    newSegments = self.trnConnections.createSegments(cellIndices)
    self.trnConnections.growSynapses(newSegments, l6Pattern, 1.0)

    # print("Learning L6 SDR:", l6Pattern,
    #       "new segments: ", newSegments,
    #       "cells:", self.trnConnections.mapSegmentsToCells(newSegments))


  def deInactivateCells(self, l6Input):
    """
    Activate trnCells according to the l6Input. These in turn will impact 
    bursting mode in relay cells that are connected to these trnCells.
    Given the feedForwardInput, compute which cells will be silent, tonic,
    or bursting.
    
    :param l6Input:

    :return: nothing
    """

    # Figure out which TRN cells recognize the L6 pattern.
    self.trnOverlaps = self.trnConnections.computeActivity(l6Input, 0.5)
    self.activeTRNSegments = np.flatnonzero(
      self.trnOverlaps >= self.trnActivationThreshold)
    self.activeTRNCellIndices = self.trnConnections.mapSegmentsToCells(
      self.activeTRNSegments)

    # print("trnOverlaps:", self.trnOverlaps,
    #       "active segments:", self.activeTRNSegments)
    for s, idx in zip(self.activeTRNSegments, self.activeTRNCellIndices):
      print(self.trnOverlaps[s], idx, self.trnIndextoCoord(idx))


    # Figure out which relay cells have dendrites in de-inactivated state
    self.relayOverlaps = self.relayConnections.computeActivity(
      self.activeTRNCellIndices, 0.5
    )
    self.activeRelaySegments = np.flatnonzero(
      self.relayOverlaps >= self.relayThreshold)
    self.burstReadyCellIndices = self.relayConnections.mapSegmentsToCells(
      self.activeRelaySegments)

    self.burstReadyCells.reshape(-1)[self.burstReadyCellIndices] = 1


  def computeFeedForwardActivity(self, feedForwardInput):
    """
    Activate trnCells according to the l6Input. These in turn will impact
    bursting mode in relay cells that are connected to these trnCells.
    Given the feedForwardInput, compute which cells will be silent, tonic,
    or bursting.

    :param feedForwardInput:
      a numpy matrix of shape relayCellShape containing 0's and 1's

    :return:
      feedForwardInput is modified to contain 0, 1, or 2. A "2" indicates
      bursting cells.
    """
    feedForwardInput += self.burstReadyCells * feedForwardInput


  def reset(self):
    """
    Set everything back to zero
    """
    self.trnOverlaps = []
    self.activeTRNSegments = []
    self.activeTRNCellIndices = []
    self.relayOverlaps = []
    self.activeRelaySegments = []
    self.burstReadyCellIndices = []
    self.burstReadyCells = np.zeros((self.relayWidth, self.relayHeight))


  def trnCellIndex(self, coord):
    """
    Map a 2D coordinate to 1D cell index.

    :param coord: a 2D coordinate

    :return: integer index
    """
    return coord[1] * self.trnWidth + coord[0]


  def trnIndextoCoord(self, i):
    """
    Map 1D cell index to a 2D coordinate

    :param i: integer 1D cell index

    :return: (x, y), a 2D coordinate
    """
    x = i % self.trnWidth
    y = i / self.trnWidth
    return x, y


  def relayCellIndex(self, coord):
    """
    Map a 2D coordinate to 1D cell index.

    :param coord: a 2D coordinate

    :return: integer index
    """
    return coord[1] * self.relayWidth + coord[0]


  def relayIndextoCoord(self, i):
    """
    Map 1D cell index to a 2D coordinate

    :param i: integer 1D cell index

    :return: (x, y), a 2D coordinate
    """
    x = i % self.relayWidth
    y = i / self.relayWidth
    return x, y


  def _initializeTRNToRelayCellConnections(self):
    """
    Initialize TRN to relay cell connectivity. For each relay cell, create a
    dendritic segment for each TRN cell it connects to.
    """
    for x in range(self.relayWidth):
      for y in range(self.relayHeight):

        # Create one dendrite for each trn cell that projects to this relay cell
        # This dendrite contains one synapse corresponding to this TRN->relay
        # connection.
        relayCellIndex = self.relayCellIndex((x,y))
        trnCells = self._preSynapticTRNCells(x, y)
        for trnCell in trnCells:
          newSegment = self.relayConnections.createSegments([relayCellIndex])
          self.relayConnections.growSynapses(newSegment,
                                             [self.trnCellIndex(trnCell)], 1.0)


  def _preSynapticTRNCells(self, i, j):
    """
    Given a relay cell at the given coordinate, return a list of the (x,y)
    coordinates of all TRN cells that project to it.

    :param relayCellCoordinate:

    :return:
    """
    xmin = max(i - 1, 0)
    xmax = min(i + 2, self.trnWidth)
    ymin = max(j - 1, 0)
    ymax = min(j + 2, self.trnHeight)
    trnCells = [
      (x, y) for x in range(xmin, xmax) for y in range(ymin, ymax)
    ]

    return trnCells