def _adaptSynapses(self, inputVector, activeColumns, predictedActiveCells):
    """
    This is the primary learning method. It updates synapses' permanence based
    on the bottom-up input to the TP and the TP's active cells.
    For each active cell, its synapses' permanences are updated as follows:

    1. if pre-synaptic input is ON due to a correctly predicted cell,
       increase permanence by _synPredictedInc
    2. else if input is ON due to an active cell, increase permanence by
       _synPermActiveInc
    3. else input is OFF, decrease permanence by _synPermInactiveDec

    Parameters:
    ----------------------------
    inputVector:    a numpy array whose ON bits represent the active cells from
                    temporal memory
    activeColumns:  an array containing the indices of the columns that
                    survived the inhibition step
    predictedActiveCells: a numpy array with numInputs elements. A 1 indicates
                          that this cell switched from predicted state in
                          the previous time step to active state in the current
                          timestep
    """
    inputIndices = numpy.where(inputVector > 0)[0]
    predictedIndices = numpy.where(predictedActiveCells > 0)[0]
    permChanges = numpy.zeros(self._numInputs)

    # Decrement inactive TM cell -> active TP cell connections
    permChanges.fill(-1 * self._synPermInactiveDec)

    # Increment active TM cell -> active TP cell connections
    permChanges[inputIndices] = self._synPermActiveInc

    # Increment correctly predicted TM cell -> active TP cell connections
    permChanges[predictedIndices] = self._synPredictedInc

    if self._spVerbosity > 4:
      print "\n============== _adaptSynapses ======"
      print "Active input indices:",inputIndices
      print "predicted input indices:",predictedIndices
      print "\n============== _adaptSynapses ======\n"

    for i in activeColumns:
      # Get the permanences of the synapses of TP cell i
      perm = self._permanences.getRow(i)

      # Only consider connections in column's potential pool (receptive field)
      maskPotential = numpy.where(self._potentialPools.getRow(i) > 0)[0]
      perm[maskPotential] += permChanges[maskPotential]
      self._updatePermanencesForColumn(perm, i, raisePerm=False)