예제 #1
0
func (sp *SpatialPooler) getNeighborsND(columnIndex int, dimensions []int, radius int, wrapAround bool) []int {
	if len(dimensions) < 1 {
		panic("Dimensions empty")
	}

	bounds := append(dimensions[1:], 1)
	bounds = utils.RevCumProdInt(bounds)

	columnCoords := make([]int, len(bounds))
	for j := 0; j < len(bounds); j++ {
		columnCoords[j] = utils.Mod(columnIndex/bounds[j], dimensions[j])
	}

	rangeND := make([][]int, len(dimensions))
	for i := 0; i < len(dimensions); i++ {
		if wrapAround {
			cRange := make([]int, (radius*2)+1)
			for j := 0; j < (2*radius)+1; j++ {
				cRange[j] = utils.Mod((columnCoords[i]-radius)+j, dimensions[i])
			}
			rangeND[i] = cRange
		} else {
			var cRange []int
			for j := 0; j < (radius*2)+1; j++ {
				temp := columnCoords[i] - radius + j
				if temp >= 0 && temp < dimensions[i] {
					cRange = append(cRange, temp)
				}
			}
			rangeND[i] = cRange
		}
	}

	cp := utils.CartProductInt(rangeND)
	var neighbors []int
	for i := 0; i < len(cp); i++ {
		val := utils.DotInt(bounds, cp[i])
		if val != columnIndex && !utils.ContainsInt(val, neighbors) {
			neighbors = append(neighbors, val)
		}
	}

	return neighbors
}
예제 #2
0
func (sp *SpatialPooler) avgConnectedSpanForColumnND(index int) float64 {
	dimensions := sp.InputDimensions

	bounds := append(dimensions[1:], 1)
	bounds = utils.RevCumProdInt(bounds)

	connected := sp.connectedSynapses.GetRowIndices(index)
	if len(connected) == 0 {
		return 0
	}

	maxCoord := make([]int, len(dimensions))
	minCoord := make([]int, len(dimensions))
	inputMax := 0
	for i := 0; i < len(dimensions); i++ {
		if dimensions[i] > inputMax {
			inputMax = dimensions[i]
		}
	}
	for i := 0; i < len(maxCoord); i++ {
		maxCoord[i] = -1.0
		minCoord[i] = inputMax
	}
	//calc min/max of (i/bounds) % dimensions
	for _, val := range connected {
		for j := 0; j < len(dimensions); j++ {
			coord := (val / bounds[j]) % dimensions[j]
			if coord > maxCoord[j] {
				maxCoord[j] = coord
			}
			if coord < minCoord[j] {
				minCoord[j] = coord
			}
		}
	}

	sum := 0
	for i := 0; i < len(dimensions); i++ {
		sum += maxCoord[i] - minCoord[i] + 1
	}

	return float64(sum) / float64(len(dimensions))
}