Algoritmo per la classificazione best-effort di vettore
-
21-09-2019 - |
Domanda
Date le quattro vettori binari che rappresentano "classi":
[1,0,0,0,0,0,0,0,0,0]
[0,0,0,0,0,0,0,0,0,1]
[0,1,1,1,1,1,1,1,1,0]
[0,1,0,0,0,0,0,0,0,0]
Quali metodi sono disponibili per classificare un vettore di valori in virgola mobile in una di queste "classi"?
arrotondamento di base funziona nella maggior parte dei casi:
round([0.8,0,0,0,0.3,0,0.1,0,0,0]) = [1 0 0 0 0 0 0 0 0 0]
Ma come posso gestire alcune interferenze?
round([0.8,0,0,0,0.6,0,0.1,0,0,0]) != [1 0 0 0 0 1 0 0 0 0]
Questo secondo caso dovrebbe essere una migliore corrispondenza per miliardo, ma invece, ho perso la soluzione completamente in quanto non v'è alcuna corrispondenza chiara.
Voglio usare MATLAB per questo compito.
Soluzione
Trova il SSD (somma delle differenze al quadrato) del vostro vettore di prova con ogni "classe "e utilizzare quello con il minor SSD.
Ecco po 'di codice: ho aggiunto un 0
alla fine del vettore di prova che hai fornito perché era solo 9 cifre, mentre le classi avevano 10
CLASSES = [1,0,0,0,0,0,0,0,0,0
0,0,0,0,0,0,0,0,0,1
0,1,1,1,1,1,1,1,1,0
0,1,0,0,0,0,0,0,0,0];
TEST = [0.8,0,0,0,0.6,0,0.1,0,0,0];
% Find the difference between the TEST vector and each row in CLASSES
difference = bsxfun(@minus,CLASSES,TEST);
% Class differences
class_diff = sum(difference.^2,2);
% Store the row index of the vector with the minimum difference from TEST
[val CLASS_ID] = min(class_diff);
% Display
disp(CLASSES(CLASS_ID,:))
A scopo illustrativo, difference
assomiglia a questo:
0.2 0 0 0 -0.6 0 -0.1 0 0 0
-0.8 0 0 0 -0.6 0 -0.1 0 0 1
-0.8 1 1 1 0.4 1 0.9 1 1 0
-0.8 1 0 0 -0.6 0 -0.1 0 0 0
E la distanza di ogni classe da TEST assomiglia a questo, class_diff
:
0.41
2.01
7.61
2.01
E ovviamente, il primo è la migliore partita in quanto ha la minima differenza.
Altri suggerimenti
Questa è la stessa cosa di Jacob ha fatto, solo con quattro diverse misure di distanza:
%%
CLASSES = [1,0,0,0,0,0,0,0,0,0
0,0,0,0,0,0,0,0,0,1
0,1,1,1,1,1,1,1,1,0
0,1,0,0,0,0,0,0,0,0];
TEST = [0.8,0,0,0,0.6,0,0.1,0,0,0];
%%
% sqrt( sum((x-y).^2) )
euclidean = sqrt( sum(bsxfun(@minus,CLASSES,TEST).^2, 2) );
% sum( |x-y| )
cityblock = sum(abs(bsxfun(@minus,CLASSES,TEST)), 2);
% 1 - dot(x,y)/(sqrt(dot(x,x))*sqrt(dot(y,y)))
cosine = 1 - ( CLASSES*TEST' ./ (norm(TEST)*sqrt(sum(CLASSES.^2,2))) );
% max( |x-y| )
chebychev = max( abs(bsxfun(@minus,CLASSES,TEST)), [], 2 );
dist = [euclidean cityblock cosine chebychev];
%%
[minDist classIdx] = min(dist);
Scegli quello che ti piace:)
Un semplice algoritmo di Euclide distanza dovrebbe essere sufficiente. La classe con la distanza minima al punto sarebbe il vostro candidato.