Skip to content

Instantly share code, notes, and snippets.

@Higgcz
Created November 7, 2012 18:07
Show Gist options
  • Save Higgcz/4033300 to your computer and use it in GitHub Desktop.
Save Higgcz/4033300 to your computer and use it in GitHub Desktop.
Simple Perceptron algorithm which divide the input space with a linear decision boundary.
function [ model ] = perceptron( data, options )
%PERCEPTRON
%
% INPUT:
% data : struct [ 1xn ] data for training the classifier
% .X
% .y
% limit : int [ 1x1 ] maximum number of iteration
% options : struc [ --- ]
% .limit : int [ 1x1 ] maximum number of iteration
% .method : string [ --- ]
% 'normal' ... for correct the v-function get first wrong classify point
% 'max' ... for correct the v-function get point with maximal error
% 'min' ... for correct the v-function get point with minimal error
% .shuffle : bool
% true ... before next iteration - shuffle data
% .divide : bool
% true ... divide data before added (1/iteration)
%
% OUTPUT:
% model ... struct
% .X ... same as input
% .y ... same as input
% .v ... classifier parameters
% .err ... classification error
% .fun ... 'perceptron_classifier'
%
%
%% Prepare input
data = c2s(data);
if ( ~exist('options', 'var') ),
options = struct('method', 'normal', 'shuffle', 'false', 'divide', 'false');
else
options = c2s(options);
end;
if ( ~isfield(options, 'method') ),
options.method = 'normal';
end;
if ( ~isfield(options, 'shuffle') ),
options.shuffle = false;
end;
if ( ~isfield(options, 'divide') ),
options.divide = false;
end;
if ( ~isfield(options, 'limit') ),
options.limit = 1e2;
end;
%% Prepare output
v = zeros(size(data.X, 1) + 1, 1);
err = zeros(1, options.limit);
%% Prepare training data
id1 = find(data.y == 1);
id2 = find(data.y == 2);
z = [data.X; ones(1, size(data.X, 2))];
z(:,id2) = z(:,id2) * (-1);
%% Training
idt = 1;
count = 1;
while ( ~isempty(idt) && count < options.limit + 1 ),
div = 1;
if ( options.divide == 1 ), div = 1/count; end;
v = v + div * z(:, idt(1));
if ( options.shuffle == 1 ),
z = z(:, randperm(length(z)));
end;
res = z' * v;
if ( strcmp(options.method, 'normal') ), idt = find(res <= 0);
elseif ( strcmp(options.method, 'max') ), idt = find(min(res) == res & res <= 0);
elseif ( strcmp(options.method, 'min') ),
maxtemp = max(res(res <= 0));
if ( ~isempty(maxtemp) ),
idt = find(res == maxtemp);
else
idt = [];
end;
end;
err(count) = sum(res <= 0);
count = count + 1;
end;
%% Erase useless elements
err(err == 0) = [];
%% Fill output
model.X = data.X;
model.y = data.y;
model.v = v;
model.err = err;
model.fun = 'perceptron_classifier';
end
function classif = perceptron_classifier(data, model)
z = [ data; data.^2; data(1,:) .* data(2,:); ones(1, size(data, 2)) ];
res = z' * model.v;
classif = sign(res);
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment