[5] | 1 | function w = incsvc(a,ktype,par,C) |
---|
| 2 | %INCSVC Incremental support vector classifier |
---|
| 3 | % |
---|
| 4 | % W = INCSVC(A,KTYPE,PAR,C) |
---|
| 5 | % |
---|
| 6 | % INPUT |
---|
| 7 | % A Dataset |
---|
| 8 | % KTYPE Type of the kernel (optional; default: 'p') |
---|
| 9 | % PAR Kernel parameter (optional; default: 1) |
---|
| 10 | % C Regularization parameter (optional; default: 1) |
---|
| 11 | % |
---|
| 12 | % OUTPUT |
---|
| 13 | % W Mapping: Support Vector Classifier |
---|
| 14 | % |
---|
| 15 | % DESCRIPTION |
---|
| 16 | % Optimizes a support vector classifier for the dataset A by an |
---|
| 17 | % incremental procedure to perform the quadratic programming. The |
---|
| 18 | % classifier can be of one of the types as defined by PROXM. Default is |
---|
| 19 | % linear (TYPE = 'p', PAR = 1). The kernel computation is done by |
---|
| 20 | % INCKERNEL which is more lightweight than PROXM. C < 1 allows for |
---|
| 21 | % more class overlap. Default C = 1. |
---|
| 22 | % |
---|
| 23 | % See also ADD_OBJ_CL, SVC, INCKERNEL |
---|
| 24 | |
---|
| 25 | % Copyright: D.M.J. Tax, D.M.J.Tax@prtools.org |
---|
| 26 | % Faculty EWI, Delft University of Technology |
---|
| 27 | % P.O. Box 5031, 2600 GA Delft, The Netherlands |
---|
| 28 | |
---|
| 29 | if nargin < 4 | isempty(C) |
---|
| 30 | C = 1; |
---|
| 31 | prwarning(3,'Regularization parameter C set to 1\n'); |
---|
| 32 | end |
---|
| 33 | if nargin < 3 | isempty(par) |
---|
| 34 | par = 1; |
---|
| 35 | prwarning(3,'Kernel parameter par set to 1\n'); |
---|
| 36 | end |
---|
| 37 | if nargin < 2 | isempty(ktype) |
---|
| 38 | ktype = 'p'; |
---|
| 39 | prwarning(3,'Polynomial kernel type is used\n'); |
---|
| 40 | end |
---|
| 41 | if nargin < 1 | isempty(a) |
---|
| 42 | w = mapping(mfilename,{ktype,par,C}); |
---|
| 43 | w = setname(w,'Inc. Support Vector Classifier'); |
---|
| 44 | return; |
---|
| 45 | end |
---|
| 46 | |
---|
| 47 | if ~isa(ktype,'mapping') %training |
---|
| 48 | %Basic sizes:: |
---|
| 49 | [N,k,c] = getsize(a); |
---|
| 50 | %kernel definition: |
---|
| 51 | kernel = 'inckernel'; |
---|
| 52 | kpar.type = ktype; |
---|
| 53 | kpar.s = par; |
---|
| 54 | %setting for displaying: (I know you can program it shorter, but this is |
---|
| 55 | %more clear): |
---|
| 56 | if N>=1000 |
---|
| 57 | dodisplay = 1; |
---|
| 58 | else |
---|
| 59 | dodisplay = 0; |
---|
| 60 | end |
---|
| 61 | |
---|
| 62 | if c==2 |
---|
| 63 | % randomize the data: |
---|
| 64 | %I = randperm(N); a = a(I,:); |
---|
| 65 | a = unrandomize(a); |
---|
| 66 | |
---|
| 67 | % settings for the program: |
---|
| 68 | global X_incremental; |
---|
| 69 | X_incremental = +a; |
---|
| 70 | y = 3 - 2*getnlab(a); |
---|
| 71 | |
---|
| 72 | % here we go: |
---|
| 73 | alf = zeros(N,1); % weights |
---|
| 74 | grad = []; % the gradient of all seen objects |
---|
| 75 | setR = []; % 'rest' set |
---|
| 76 | Kr = []; % kernel matrix of the rest objects(RxS) |
---|
| 77 | setD = []; |
---|
| 78 | setS = []; |
---|
| 79 | setE = []; |
---|
| 80 | Ke = []; |
---|
| 81 | Ks = 0; |
---|
| 82 | b = 0; |
---|
| 83 | R = inf; |
---|
| 84 | tol = 1e-8; |
---|
| 85 | |
---|
| 86 | % startup: |
---|
| 87 | for c=1:N |
---|
| 88 | if dodisplay & mod(c,100)==0 |
---|
| 89 | fprintf('%d/%d ',c,N); |
---|
| 90 | end |
---|
[103] | 91 | dd_message(6,'ADD obj %d\n',c); |
---|
[5] | 92 | add_obj_cl; |
---|
[103] | 93 | %fprintf('%d [%f',c,alf(setS(1))); |
---|
| 94 | %for jj=2:length(setS) |
---|
| 95 | % fprintf(' %f',alf(setS(jj))); |
---|
| 96 | %end |
---|
| 97 | %fprintf(']\n'); |
---|
[5] | 98 | end |
---|
| 99 | |
---|
| 100 | % make the classifier |
---|
[103] | 101 | W.K = kernel; |
---|
| 102 | W.par = kpar; |
---|
[5] | 103 | J = [setS;setE]; |
---|
| 104 | W.J = J; |
---|
| 105 | W.sv = X_incremental(J,:); |
---|
[103] | 106 | W.alf = y(J).*alf(J,:); |
---|
[5] | 107 | W.b = b; |
---|
| 108 | w = mapping(mfilename,'trained',W,getlablist(a),k,2); |
---|
| 109 | w = setname(w,'Inc. Support Vector Classifier'); |
---|
| 110 | |
---|
| 111 | else % multi-class classifier: |
---|
| 112 | |
---|
| 113 | w = mclassc(a,mapping(mfilename,{ktype,par,C})); |
---|
| 114 | |
---|
| 115 | end |
---|
| 116 | |
---|
| 117 | else %execution |
---|
| 118 | W = +ktype; |
---|
| 119 | [n,d] = size(a); |
---|
| 120 | laba = getlab(a); |
---|
| 121 | orga = a; |
---|
| 122 | a = +a; |
---|
| 123 | global X_incremental; |
---|
| 124 | X_incremental = [W.sv; zeros(1,d)]; |
---|
| 125 | nra = size(W.sv,1)+1; I = 1:nra; |
---|
| 126 | out = repmat(W.b,n,1); |
---|
| 127 | for i=1:n |
---|
| 128 | X_incremental(nra,:) = a(i,:); |
---|
[103] | 129 | Ka = feval(W.K,W.par,nra,I); |
---|
| 130 | out(i) = out(i) + Ka(1:(nra-1))*W.alf; |
---|
[5] | 131 | end |
---|
| 132 | newout = [out -out]; |
---|
| 133 | w = setdat(orga,newout,ktype); |
---|
| 134 | end |
---|
| 135 | |
---|
| 136 | return |
---|
| 137 | |
---|
| 138 | |
---|
| 139 | |
---|
| 140 | function a= unrandomize(a); |
---|
| 141 | % Unrandomize a dataset; |
---|
| 142 | |
---|
| 143 | [n,k,c]=getsize(a); |
---|
| 144 | if c~=2 |
---|
| 145 | error('I assume 2 classes'); |
---|
| 146 | end |
---|
| 147 | |
---|
| 148 | nlab = getnlab(a); |
---|
| 149 | I1 = find(nlab==1); |
---|
| 150 | I2 = find(nlab==2); |
---|
| 151 | |
---|
| 152 | if length(I1)<length(I2) |
---|
| 153 | cmin = length(I1); |
---|
| 154 | else |
---|
| 155 | cmin = length(I2); |
---|
| 156 | tmpI = I1; |
---|
| 157 | I1 = I2; |
---|
| 158 | I2 = tmpI; |
---|
| 159 | end |
---|
| 160 | |
---|
| 161 | J=[]; |
---|
| 162 | J(1:2:2*cmin) = I1; |
---|
| 163 | J(2:2:2*cmin) = I2(1:cmin); |
---|
| 164 | J = [J,I2((cmin+1):end)']; |
---|
| 165 | a = a(J,:); |
---|
| 166 | |
---|
| 167 | return |
---|