Mark Jerzykowski
Mark Jerzykowski

Reputation: 982

Matlab Vectorization of Multivariate Gaussian Basis Functions

I have the following code for calculating the result of a linear combination of Gaussian functions. What I'd really like to do is to vectorize this somehow so that it's far more performant in Matlab.

Note that y is a column vector (output), x is a matrix where each column corresponds to a data point and each row corresponds to a dimension (i.e. 2 rows = 2D), variance is a double, gaussians is a matrix where each column is a vector corresponding to the mean point of the gaussian and weights is a row vector of the weights in front of each gaussian. Note that the length of weights is 1 bigger than gaussians as weights(1) is the 0th order weight.

function [ y ] = CalcPrediction( gaussians, variance, weights, x )

basisFunctions = size(gaussians, 2);
xvalues = size(x, 2);
if length(weights) ~= basisFunctions + 1
    ME = MException('TRAIN:CALC', 'The number of weights should be equal to the number of basis functions plus one');
    throw(ME);
end


y = weights(1) * ones(xvalues, 1);

for xIdx = 1:xvalues
    for i = 1:basisFunctions
        diff = x(:, xIdx) - gaussians(:, i);
        y(xIdx) = y(xIdx) + weights(i+1) * exp(-(diff')*diff/(2*variance));
    end
end

end

You can see that at the moment I simply iterate over the x vectors and then the gaussians inside 2 for loops. I'm hoping that this can be improved - I've looked at meshgrid but that seems to only apply to vectors (and I have matrices)

Thanks.

Upvotes: 0

Views: 350

Answers (1)

Mark Mikofski
Mark Mikofski

Reputation: 20198

Try this

diffx = bsxfun(@minus,x,permute(gaussians,[1,3,2])); % binary operation with singleton expansion
diffx2 = squeeze(sum(diffx.^2,1)); % dot product, shape is now [XVALUES,BASISFUNCTIONS]
weight_col = weights(:); % make sure weights is a column vector
y = exp(-diffx2/2/variance)*weight_col(2:end); % a column vector of length XVALUES

Note, I changed diff to diffx since diff is a builtin. I'm not sure this will improve performance as allocating arrays will offset increase by vectorization.

Upvotes: 1

Related Questions