fenestration.pooling.gaussian#

fenestration.pooling.gaussian(x: float | ndarray, std_dev: float | None = 1) → ndarray#

Compute simple gaussian with mean 0, and adjustable std dev.

Possible window function, giving the weighting in each direction for the spatial pooling performed during the construction of visual metamers.

Parameters:
  • x – The distance in a direction

  • std_dev – The standard deviation of the Gaussian window.

Returns:

array – The value of the window at each value of x

Notes

We normalize in here in order to make sure that the windows sum to 1. In order to do that, we note that each Gaussian is centered at integer x values: 0, 1, 2, 3, etc. If we’re summing at x=0, we then note that the first window will be centered there and so have its max amplitude, its two nearest neighbors will be 1 away from their center (these Gaussians are symmetric), their two nearest neighbors will be 2 away from their center, etc. Therefore, we’ll have one Gaussian at max value (1), two at \(\exp(\frac{-1^2}{2\sigma^2})\), two at \(\exp(\frac{-2^2}{2\sigma^2})\), etc.

Summing at this location will give us the value we need to normalize by, \(S\). We work through this with \(\sigma=1\):

\[\begin{split}S &= 1 + 2 * \exp(\frac{-(1)^2}{2\sigma^2}) + 2 * \exp(\frac{-(2)^2}{2\sigma^2}) + ... \\ S &= 1 + 2 * \sum_{n=1}^{\inf} \exp(\frac{-n^2}{2}) \\ S &= -1 + 2 * \sum_{n=0}^{\inf} \exp(\frac{-n^2}{2})\end{split}\]

And we’ve stored this number as the constant GAUSSIAN_SUM (the infinite sum computed in the equation above was computed using Wolfram Alpha).

When std_dev>1, the windows overlap more. As with the probability density function of a normal distribution, we divide by std_dev to keep the integral constant for different values of std_dev (though the integral is not 1). This means that summing across multiple windows will still give us a value of 1.