• Non ci sono risultati.

ƒ Matlab function per la stima dell’SNR sul tracciato EMG.

N/A
N/A
Protected

Academic year: 2021

Condividi "ƒ Matlab function per la stima dell’SNR sul tracciato EMG. "

Copied!
33
0
0

Testo completo

(1)

APPENDICE B

PROGRAMMI MATLAB SVILUPPATI

ƒ Matlab function per l’applicazione del filtro di Kalman all’elaborazione offline.

function [Xres] = mio_kalman(sign) L=length(sign);

% Definizioni dei valori interni alle matrici del filtro

% varianza errore valore iniziale e1 = 0;

% varianza errore stato iniziale d=diff(sign);

q1=cov(d);

% varianza rumore sulla misura r1 = 0.1.*[1 0 0; 0 1 0; 0 0 1];

% Inizializzazione dello stato del filtro Xn = [0; 0; 0];

P = zeros(3);

% Definizioni delle matrici del filtro PHI = eye(3);

Q = q1;

R = r1;

C = eye(3);

a = [0; 0; 0];

b = zeros(3);

% Inizializzazione del vettore dei risultati Xres = []; Pres = [];

% Loop per 't' step sign = sign';

for t = 1:L

Xr = sign(:,t);

Z = Xr;

% Lettura delle misure affette da rumore Xp=a;

Pp=b;

% Calcolo della matrice di guadagno del filtro di Kalman K = Pp * C' * inv(C * Pp * C' + R);

% Aggiornamento della stima dello stato Xn = Xp + K * (Z - C * Xp);

(2)

% Aggiornamento della varianza dei disturbi sullo stato e aggiornamento del ciclo

Pn = (eye(3) - K * C)* Pp;

% Aggiornamento dello stato

a = PHI * Xn; %%stima dello stato futuro a k+1

% Aggiornamento della stima della varianza dell'errore sullo stato k+1 b = PHI * Pn * PHI' + Q;

% Memorizzazione dei risultati XRres(:,t) = Xr;

Xres(:,t) = Xn;

end

Xres=Xres';

XRres=XRres';

%Visualizzazione

subplot(3,1,1), plot(tempo(1:length(Xres(:,1))),Xres(:,1)+1);

hold;

plot(tempo(1:length(Xres)),XRres(:,1)-1,'g');

xlabel('time (s)');

ylabel('V(Volt)');

legend('C1 filtrato','C1 non filtrato');

subplot(3,1,2), plot(tempo(1:length(Xres)),Xres(:,2)+1);

hold;

plot(tempo(1:length(Xres)),XRres(:,2)-1,'g');

xlabel('time (s)');

ylabel('V(Volt)');

legend('C2 filtrato','C2 non filtrato');

subplot(3,1,3), plot(tempo(1:length(Xres)),Xres(:,3)+3);

hold;

plot(tempo(1:length(Xres)),XRres(:,3)-3,'g');

xlabel('time (s)');

ylabel('V(Volt)');

legend('C3 filtrato','C3 non filtrato');

ƒ Matlab function per la stima dell’SNR sul tracciato EMG.

function [SNR N] = signaltonoise(C)

%==============%

%%%%%RUMORE%%%%%

%==============%

for i = 1:3

noise (:,i) = C(2000:2999,i); %Creazione della matrice di rumore

P_noise(:,i)= sqrt(sum(noise(:,i).*conj(noise(:,i)))/1000); %Calcolo della potenza di rumore

%===============%

%%%%%SEGNALE%%%%%

%===============%

L = length(C);

rect_elettrodo = abs(C(2000:L,i)); %rettifico il canale

(3)

M = max(rect_elettrodo); %individuo l'ampiezza massima del segnale originario

for n = 1:L-2000

b = rect_elettrodo(n);

if b == M

max_sample = n; %individuo il campione corrispondente all'ampiezza massima

end;

end;

inf = max_sample - 500;

sup = max_sample + 499;

signal(:,i) = C(inf:sup,i);

P_signal (:,i) = sqrt(sum(signal(:,i).*conj(signal(:,i)))/1000); %Calcolo della potenza di segnale

%====Calcolo dell' SNR

SNR(:,i) = P_signal/P_noise;

N(:,i)= 10*log10(SNR(:,i));

end;

end

ƒ Matlab function per l’estrazione dell’inviluppo lineare dai segnali EMG.

function[env]=Inviluppo(sign)

[a,b]=butter(5,10/2000,'low'); %crea il passa-basso per lo smoothing (Fcutoff= 10Hz, Fc=2000Hz, ordine 5)

env = filter(a,b,abs(sign));

end

ƒ Matlab function per il calcolo dell’onset su segnali EMG.

function [sampleno reston] = solonset(y,a,b,c,d)

%y: segnale su cui calcolare l'onset

%[a,b]: segmento di segnale su cui calcolare la soglia

%[c,d]: inizio e fine dell'intero tracciato EMG da analizzare

reston = mean(y(a:b)) + 3*std(y(a:b));

x = 0;

for n = c:d

if y(n) >= reston x = x+1;

else

x = 0;

end

if x == 50

sampleno = n - 49;

break end

end;

(4)

ƒ Codice Matlab per l’elaborazione di segnali EMG con calcolo dei parametri teta e rappresentazione degli onset sugli inviluppi.

n = input('Inserisci il numero di acquisizioni per il movimento: ');

w = input('inserisci la lunghezza del segnale da analizzare: ');

c = 1;

d = w;

a = input('inserisci il sample inf di riposo pre-burnst [a]: ');

b = input('inserisci il sample sup di riposo pre-burnst [b]: ');

for z = 1:n

%---%

%Separazione e rettifica dei canali dal file di acquisizione originario da

%Grass

sign = input('inserisci il file della misura ');

[C1 C2 C3 L] = Sep_Rett (sign);

C=[C1 C2 C3];

%---%

%Estrazione degli inviluppi nella finestra di osservazione L=[3000:i]

%campioni.

for i = 1:3

S(:,i) = Inviluppo(C(:,i));

Env(:,i) = S(3000:(w+999),i);

end;

%---%

%Calcolo dell' onset (function 'solonset') sull' inviluppo dei segnali.

for i = 1:3

[sampon soglia]= solonset(Env(:,i),a,b,c,d);

on(:,i) = sampon;

soglia_on(:,i) = soglia;

end;

%---%

Rappresentazioe degli onset sugli inviluppi.

plot(Env(:,1), 'b');

xlabel('sample number');

ylabel('EMG signal');

hold on

point1=[on(1,1) on(1,1)];

point2=[0 max(Env(:,1))];

plot(point1, point2,'LineWidth',2,'Color','b');

s1=['onset1 = ', num2str(on(1,1))];

text(on(1,1)+1, max(Env(:,1)), s1, 'Color','b');

hold on

plot(Env(:,2),'r');

hold on

point3=[on(1,2) on(1,2)];

point4=[0 max(Env(:,2))];

plot(point3, point4,'LineWidth',2,'Color','r');

t1=['onset2 = ', num2str(on(1,2))];

text(on(1,2)+1, max(Env(:,2)), t1, 'Color','r');

hold on

(5)

plot(Env(:,3), 'g');

hold on

point5=[on(1,3) on(1,3)];

point6=[0 max(Env(:,3))];

plot(point5, point6,'LineWidth',2,'Color','g');

u1=['onset3 = ', num2str(on(1,3))];

text(on(1,3)+1, max(Env(:,3)), u1, 'Color','g');

hold off;

%---%

%Calcolo degli sfasamenti tra onset (parametri teta).

if on(1,1) == 0 || on(1,2) == 0 tetaon12 = 0;

else tetaon12 = abs(on(1,1) - on(1,2));

end;

if on(1,1) == 0 || on(1,3) == 0 tetaon13 = 0;

else tetaon13 = abs(on(1,1) - on(1,3));

end;

if on(1,2) == 0 || on(1,3) == 0 tetaon23 = 0;

else tetaon23 = abs(on(1,2) - on(1,3));

end;

%---%

%Creazione della matrice degli sfasamenti.

tetaon = [tetaon12 tetaon13 tetaon23];

teta(z,:) = tetaon;

clear C C1 C2 C3 Env L S i sampon sign soglia t1 u1;

%---%

end;

clear a b c d n on soglia_on tetaon tetaon12 tetaon13 tetaon23 w z;

ƒ Matlab function per la separazione dei canali dal file di acquisizione da GRASS.

function [C1 C2 C3 L] = Sep_Rett (sign)

L = length(sign);

C1 = abs(sign(1:L,2));

C2 = abs(sign(1:L,3) - 0.5);

C3 = abs(sign(1:L,4) - 0.8);

end

ƒ Matlab functions per il calcolo dei parametri dell’EMG e dell’indice SEM di ripetibilità.

%============================Calcolo dell'ARV==============================

%==========================================================================

%Il valore medio del segnale rettificato (ARV) è un descrittore di ampiezza

%del segnale EMG.

%==========================================================================

function ARV = ARV(elettrodo)

L = length(elettrodo); %intervallo di osservazione dell'EMGs

(6)

rec_ch = abs(elettrodo); %rettifica del segnale ARV = (sum(rec_ch))/L; % calcolo dell' ARV end

%==========================================================================

%============================Calcolo dell'RMS==============================

%==========================================================================

%Il Valore Efficace (RMS) è un descrittore di ampiezza del segnale EMG.

%Coincide, tra l'altro, con la potenza elettrica del segnale.

%==========================================================================

function RMS = RMS(elettrodo)

L = length(elettrodo); %intervallo di osservazione dell'EMGs square_ch = elettrodo.^2; %quadrato del segnale originario RMS = sqrt((sum(square_ch))/L); %calcolo dell'RMS

end

%==========================================================================

%=========================Calcolo della MNF================================

%==========================================================================

%La Frequenza Media (MNF) è un descrittore di frequenza del segnale EMG.

%E' definita come l’ascissa del baricentro dello spettro.

%==========================================================================

function MNF = MNF (input)

%Costruzione dello spettro di potenza FFTch = fft(input, 512);

Pch = (FFTch.*conj(FFTch))/512;

f = 2000*(0:256)/512;

m = Pch(1:257);

m=1000*m;

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

M1 = sum(f.*m');

M0 = sum(m);

MNF = M1/M0

%plot(f,m);

end

%===========================Calcolo del SEM================================

%L'Errore Standard della Media (SEM) stima l'errore sul valore medio delle

%misure di una variabile. Da esso può ricavarsi un giudizio sulla bontà

%delle misure ed è uno stimatore semplice di ripetibilità intra-soggetto.

%Dividendo il SEM per il valore medio si ottiene il SEM Normalizzato, che

%stabilisce la % di errore commessa nella misura.

function [SEM SEMN VMEDIO]= SEM(input, nr_mis)

%global par;

%global nr_mis;

sigma = std(input); %deviazione standard

(7)

VMEDIO = mean(input);

SEM = (sigma)/sqrt(nr_mis);

SEMN = 100*abs((SEM/mean(input)));

end

ƒ Codice Matlab che gestisce il test di ripetibilità del SEM.

for i = 1:3

canale = input('inserisci il canale ');

[arv rms mnf mdf variance cda cdc] = parametri(canale, nr_mis);

%matrici nr_mis x 3(C1 C2 C3) Arv(:,i) = arv';

Rms(:,i) = rms';

Mnf(:,i) = mnf';

teta(:,i) = teta';

%calcolo dei valori medi e delle deviazioni dei parametri per i 3 %Canali per un movimento.

med_arv(:,i)=mean(Arv(:,i));

dev_arv(:,i)=std(Arv(:,i));

end;

%par=Arv(:,1);

%Calcolo del sem e del semn

for j = 1:7 %tanti quanti i parametri

parametro = input('Inserisci il parametro ');

for i = 1:3

par = parametro(:,i);

[sem(j,i) semn(j,i) vmedio(j,i)] = SEM(par, nr_mis);

end;

end;

%Conformazione della matrice del SEM (analog. per SEMN):

%

%

% | sem(C1,1) sem(C2,1) sem(C3,1)|

% sem = | sem(C1,2) sem(C2,2) sem(C3,3)|

% | .... ... .. |

% | sem(C1,4) sem(C2,4) sem(C3,4)|

%=======================================================

%Matrice dei Valori Medi (sulle righe: val.medi del parametro su 3 canali;

%sulle colonne: canali) per un movimento!!!

mov = mean(vmedio,2);

ƒ Matlab function per il calcolo simultaneo dei parametri EMG.

%==Ogni uscita è un vettore dei valori del parametro corrispondente nelle=%

%======='nr_mis' acquisizioni per un canale per un dato movimento=========%

function [arv rms mnf mdf variance cda cdc] = Parametri (canale, nr_mis)

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

%%%%

for i = 1:nr_mis

arv(:,i) = ARV(canale(:,i)); %Valore Medio Rettificato

(8)

rms(:,i) = RMS(canale(:,i)); %Valore Quadratico Medio mnf(:,i) = MNF(canale(:,i)); %Frequenza Media

teta(:,i) = TETA(canale(:,i)); %Sfasamenti fra onset end;

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

end

ƒ Matlab GUI per la gestione della calibrazione e dell’inizializzazione del classificatore.

function varargout = EMGui(varargin)

gui_Singleton = 1;

gui_State = struct('gui_Name', mfilename, ...

'gui_Singleton', gui_Singleton, ...

'gui_OpeningFcn', @EMGui_OpeningFcn, ...

'gui_OutputFcn', @EMGui_OutputFcn, ...

'gui_LayoutFcn', [] , ...

'gui_Callback', []);

if nargin && ischar(varargin{1})

gui_State.gui_Callback = str2func(varargin{1});

end

if nargout

[varargout{1:nargout}] = gui_mainfcn(gui_State, varargin{:});

else

gui_mainfcn(gui_State, varargin{:});

end

% End initialization code - DO NOT EDIT

% --- Executes just before EMGui is made visible.

function EMGui_OpeningFcn(hObject, eventdata, handles, varargin)

% This function has no output args, see OutputFcn.

% hObject handle to figure

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA)

% varargin command line arguments to EMGui (see VARARGIN)

% Choose default command line output for EMGui handles.output = hObject;

% Update handles structure guidata(hObject, handles);

% UIWAIT makes EMGui wait for user response (see UIRESUME)

% uiwait(handles.figure1);

%

Elettromiografia; %apre il modello Simulink rtwbuild('Elettromiografia');% esegue il "build"

pause(1);

global conta_ext conta_flex conta_pro conta_ad conta_ab;%parametro;

conta_ext = 0;

conta_flex = 0;

conta_pro = 0;

conta_ad = 0;

conta_ab = 0;

set(handles.text3,'String','');

% --- Outputs from this function are returned to the command line.

(9)

function varargout = EMGui_OutputFcn(hObject, eventdata, handles)

% varargout cell array for returning output args (see VARARGOUT);

% hObject handle to figure

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA)

% Get default command line output from handles structure varargout{1} = handles.output;

% --- Executes on button press in pushbutton.

function pushbutton_Callback(hObject, eventdata, handles)

% hObject handle to pushbutton (see GCBO)

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA)

set_param('Elettromiografia','SimulationCommand','Connect'); %connette il modulo simulink

pause(1); %aspetta

set_param('Elettromiografia','SimulationCommand','Start');%comincia l' acquisizione

pause(2.5);

set(handles.text8,'foregroundcolor', 'b');

set(handles.text8, 'string', 'ESEGUI!');

pause(1);

set(handles.text8, 'string', '');

pause(2.5);

set_param('Elettromiografia','SimulationCommand','Stop');%termina l'acquisizione pause(1);%aspetta

set_param('Elettromiografia','SimulationCommand','Disconnect');%disconnette il modulo simulink

% --- Executes on button press in pushbutton2.

function pushbutton2_Callback(hObject, eventdata, handles)

% hObject handle to pushbutton2 (see GCBO)

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA)

% set_param('Elettromiografia','SimulationCommand','Stop');%termina l'acquisizione

% pause(1);%aspetta

% set_param('Elettromiografia','SimulationCommand','Disconnect');%disconnette il modulo simulink

% --- Executes on button press in pushbutton3.

function pushbutton3_Callback(hObject, eventdata, handles)

% hObject handle to pushbutton3 (see GCBO)

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA)

global conta_ext conta_flex conta_pro mov conta_ad conta_ab ARV_AD RMS_AD TETA_AD ARV_AB RMS_AB TETA_AB SOGLIE_FLEX SOGLIE_PRO;

global SNR_ref nr_mis ARV_EXT ARV_FLEX ARV_PRO RMS_EXT RMS_FLEX RMS_PRO TETA_EXT TETA_FLEX TETA_PRO SOGLIE_EXT SOGLIE_AD SOGLIE_AB;

set(handles.text3,'String','');

signal = evalin('base','nokalman');%prelevo dal workspace il segnale acquisito come inviluppo

C = Sep_Rett(signal);%nella matrice C ho i 3 canali utili senza il tempo

[SNR N] = signaltonoise(C); %calcolo il SNR (N in dB) dell'acquisizione sui tre canali

if SNR(1) >= SNR_ref(1) && SNR(2) >= SNR_ref(2) && SNR(3)>= SNR_ref(3) pause(0.5);

(10)

set(handles.text3,'foregroundcolor', 'g');

set(handles.text3,'String','MISURA BUONA!');

if mov == 1

conta_ext = conta_ext+1;

[arv_ext rms_ext teta_ext threshold_ext] = win_par(C);%calcolo i parametri per i 3 canali

ARV_EXT(conta_ext,:) = arv_ext;%matrice degli arv su tutte le misure(nr_mis x canali)

RMS_EXT(conta_ext,:) = rms_ext;%matrice degli rms su tutte le misure(nr_mis x canali)

TETA_EXT(conta_ext,:) = teta_ext;%matrice dei teta su tutte le misure(nr_mis x canali)

SOGLIE_EXT(conta_ext,:) = threshold_ext;%matrice delle soglie su tutte le misure(nr_mis x canali)

if conta_ext == nr_mis

set(handles.text3,'foregroundcolor', 'b');

set(handles.text3,'string', 'STOP EXTENSION!');

%salvataggio delle variabili save arv_ext ARV_EXT

save rms_ext RMS_EXT;

save teta_ext TETA_EXT;

save soglie_ext SOGLIE_EXT;

%%===PER IL CLASSIFICATORE===%%

%calcolo i valori medi dei parametri e delle soglie %si tratta di vettori (1 x canali)

ARVM_EXT = mean(ARV_EXT,1);

RMSM_EXT = mean(RMS_EXT,1);

TETAM_EXT = mean(TETA_EXT,1);

SOGLIEM_EXT = mean(SOGLIE_EXT,1);

%salvataggio delle variabili save arvm_ext ARVM_EXT;

save rmsm_ext RMSM_EXT;

save tetam_ext TETAM_EXT;

save sogliem_ext SOGLIEM_EXT;

%calcolo le dev. st. dei parametri e delle soglie %si tratta di vettori (1 x canali)

ARVDS_EXT = std(ARV_EXT,1);

RMSDS_EXT = std(RMS_EXT,1);

TETADS_EXT = std(TETA_EXT,1);

SOGLIEDS_EXT = std(SOGLIE_EXT,1);

%salvataggio delle variabili save arvds_ext ARVDS_EXT;

save rmsds_ext RMSDS_EXT;

save tetads_ext TETADS_EXT;

save soglieds_ext SOGLIEDS_EXT;

conta_ext = 0;

%%===========================%%

end

elseif mov == 2

conta_flex = conta_flex+1;

[arv_flex rms_flex teta_flex threshold_flex] = win_par(C);

ARV_FLEX(conta_flex,:) = arv_flex;%matrice degli arv su tutte le misure(nr_mis x canali)

RMS_FLEX(conta_flex,:) = rms_flex;%matrice degli rms su tutte le misure(nr_mis x canali)

TETA_FLEX(conta_flex,:) = teta_flex;%matrice dei teta su tutte le misure(nr_mis x canali)

SOGLIE_FLEX(conta_flex,:) = threshold_flex;%matrice delle soglie su tutte le misure(nr_mis x canali)

if conta_flex ==nr_mis

set(handles.text3,'foregroundcolor', 'b');

(11)

set(handles.text3,'string', 'STOP FLEXION!');

%salvataggio delle variabili save arv_flex ARV_FLEX;

save rms_flex RMS_FLEX;

save teta_flex TETA_FLEX;

save soglie_flex SOGLIE_FLEX;

%%===PER IL CLASSIFICATORE===%%

%calcolo i valori medi dei parametri e delle soglie %si tratta di vettori (1 x canali)

ARVM_FLEX = mean(ARV_FLEX,1);

RMSM_FLEX = mean(RMS_FLEX,1);

TETAM_FLEX = mean(TETA_FLEX,1);

SOGLIEM_FLEX = mean(SOGLIE_FLEX,1);

%salvataggio delle variabili save arvm_flex ARVM_FLEX;

save rmsm_flex RMSM_FLEX;

save tetam_flex TETAM_FLEX;

save sogliem_flex SOGLIEM_FLEX;

%calcolo le dev. st. dei parametri e delle soglie %si tratta di vettori (1 x canali)

ARVDS_FLEX = std(ARV_FLEX,1);

RMSDS_FLEX = std(RMS_FLEX,1);

TETADS_FLEX = std(TETA_FLEX,1);

SOGLIEDS_FLEX = std(SOGLIE_FLEX,1);

%salvataggio delle variabili save arvds_flex ARVDS_FLEX;

save rmsds_flex RMSDS_FLEX;

save tetads_flex TETADS_FLEX;

save soglieds_flex SOGLIEDS_FLEX;

conta_flex=0;

%%===========================%%

end

elseif mov == 3

conta_pro = conta_pro+1;

[arv_pro rms_pro teta_pro threshold_pro] = win_par(C);

ARV_PRO(conta_pro,:) = arv_pro;%matrice degli arv su tutte le misure(nr_mis x canali)

RMS_PRO(conta_pro,:) = rms_pro;%matrice degli rms su tutte le misure(nr_mis x canali)

TETA_PRO(conta_pro,:) = teta_pro;%matrice dei teta su tutte le misure(nr_mis x canali)

SOGLIE_PRO(conta_pro,:) = threshold_pro;%matrice delle soglie su tutte le misure(nr_mis x canali)

if conta_pro == nr_mis

set(handles.text3,'foregroundcolor', 'b');

set(handles.text3,'string','STOP PRONOSUP.!');

%salvataggio delle variabili save arv_pro ARV_PRO;

save rms_pro RMS_PRO;

save teta_pro TETA_PRO;

save soglie_pro SOGLIE_PRO;

%%===PER IL CLASSIFICATORE===%%

%calcolo i valori medi dei parametri e delle soglie %si tratta di vettori (1 x canali)

ARVM_PRO = mean(ARV_PRO,1);

RMSM_PRO = mean(RMS_PRO,1);

TETAM_PRO = mean(TETA_PRO,1);

SOGLIEM_PRO = mean(SOGLIE_PRO,1);

%salvataggio delle variabili save arvm_pro ARVM_PRO;

save rmsm_pro RMSM_PRO;

(12)

save tetam_pro TETAM_PRO;

save sogliem_pro SOGLIEM_PRO;

%calcolo le dev. st. dei parametri e delle soglie %si tratta di vettori (1 x canali)

ARVDS_PRO = std(ARV_PRO,1);

RMSDS_PRO = std(RMS_PRO,1);

TETADS_PRO = std(TETA_PRO,1);

SOGLIEDS_PRO = std(SOGLIE_PRO,1);

%salvataggio delle variabili save arvds_pro ARVDS_PRO;

save rmsds_pro RMSDS_PRO;

save tetads_pro TETADS_PRO;

save soglieds_pro SOGLIEDS_PRO;

conta_pro=0;

%%===========================%%

end

elseif mov == 4

conta_ad = conta_ad+1;

[arv_ad rms_ad teta_ad threshold_ad] = win_par(C);

ARV_AD(conta_ad,:) = arv_ad;%matrice degli arv su tutte le misure(nr_mis x canali)

RMS_AD(conta_ad,:) = rms_ad;%matrice degli rms su tutte le misure(nr_mis x canali)

TETA_AD(conta_ad,:) = teta_ad;%matrice dei teta su tutte le misure(nr_mis x canali)

SOGLIE_AD(conta_ad,:) = threshold_ad;%matrice delle soglie su tutte le misure(nr_mis x canali)

if conta_ad == nr_mis

set(handles.text3,'foregroundcolor', 'b');

set(handles.text3,'string','STOP ADDUCTION!');

%salvataggio delle variabili save arv_ad ARV_AD;

save rms_ad RMS_AD;

save teta_ad TETA_AD;

save soglie_ad SOGLIE_AD;

%===PER IL CLASSIFICATORE===%%

%calcolo i valori medi dei parametri e delle soglie %si tratta di vettori (1 x canali)

ARVM_AD = mean(ARV_AD,1);

RMSM_AD = mean(RMS_AD,1);

TETAM_AD = mean(TETA_AD,1);

SOGLIEM_AD = mean(SOGLIE_AD,1);

%salvataggio delle variabili save arvm_ad ARVM_AD;

save rmsm_ad RMSM_AD;

save tetam_ad TETAM_AD;

save sogliem_ad SOGLIEM_AD;

%calcolo le dev. st. dei parametri e delle soglie %si tratta di vettori (1 x canali)

ARVDS_AD = std(ARV_AD,1);

RMSDS_AD = std(RMS_AD,1);

TETADS_AD = std(TETA_AD,1);

SOGLIEDS_AD = std(SOGLIE_AD,1);

%salvataggio delle variabili save arvds_ad ARVDS_AD;

save rmsds_ad RMSDS_AD;

save tetads_ad TETADS_AD;

save soglieds_ad SOGLIEDS_AD;

conta_ad=0;

%%==========================%%

(13)

end

elseif mov == 5

conta_ab = conta_ab+1;

[arv_ab rms_ab teta_ab threshold_ab] = win_par(C);

ARV_AB(conta_ab,:) = arv_ab;%matrice degli arv su tutte le misure(nr_mis x canali)

RMS_AB(conta_ab,:) = rms_ab;%matrice degli rms su tutte le misure(nr_mis x canali)

TETA_AB(conta_ab,:) = teta_ab;%matrice dei teta su tutte le misure(nr_mis x canali)

SOGLIE_AB(conta_ab,:) = threshold_ab;%matrice delle soglie su tutte le misure(nr_mis x canali)

if conta_ab == nr_mis

set(handles.text3,'foregroundcolor', 'b');

set(handles.text3,'string','STOP ABDUCTION!');

%salvataggio delle variabili save arv_ab ARV_AB;

save rms_ab RMS_AB;

save teta_ab TETA_AB;

save soglie_ab SOGLIE_AB;

%%===PER IL CLASSIFICATORE===%%

%calcolo i valori medi dei parametri e delle soglie %si tratta di vettori (1 x canali)

ARVM_AB = mean(ARV_AB,1);

RMSM_AB = mean(RMS_AB,1);

TETAM_AB = mean(TETA_AB,1);

SOGLIEM_AB = mean(SOGLIE_AB,1);

%salvataggio delle variabili save arvm_ab ARVM_AB;

save rmsm_ab RMSM_AB;

save tetam_ab TETAM_AB;

save sogliem_ab SOGLIEM_AB;

%calcolo le dev. st. dei parametri e delle soglie %si tratta di vettori (1 x canali)

ARVDS_AB = std(ARV_AB,1);

RMSDS_AB = std(RMS_AB,1);

TETADS_AB = std(TETA_AB,1);

SOGLIEDS_AB = std(SOGLIE_AB,1);

%salvataggio delle variabili save arvds_ab ARVDS_AB;

save rmsds_ab RMSDS_AB;

save tetads_ab TETADS_AB;

save soglieds_ab SOGLIEDS_AB;

conta_ab=0;

%%===========================%%

end end

else pause(0.5);

set(handles.text3,'foregroundcolor', 'r');

set(handles.text3,'String','RIPETERE LA MISURA!');

end

% --- Executes on selection change in listbox1.

function listbox1_Callback(hObject, eventdata, handles)

% hObject handle to listbox1 (see GCBO)

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA)

% Hints: contents = get(hObject,'String') returns listbox1 contents as cell array

% contents{get(hObject,'Value')} returns selected item from listbox1

(14)

global SNR_ref mov;

list_movements = get(handles.listbox1,'String');

index_selected = get(handles.listbox1,'Value');

if strcmp(list_movements(index_selected),'Estensione') SNR_ref = [3 3 3];

mov=1;

elseif strcmp(list_movements(index_selected),'Flessione') SNR_ref = [3 3 3];

mov=2;

elseif strcmp(list_movements(index_selected),'Pronosupinazione') SNR_ref = [2 2 2];

mov=3;

elseif strcmp(list_movements(index_selected),'Adduzione') SNR_ref = [2 2 2];

mov=4;

elseif strcmp(list_movements(index_selected),'Abduzione') SNR_ref = [1.5 1.5 1.5];

mov=5;

end

set(handles.text4, 'string', SNR_ref)

% --- Executes during object creation, after setting all properties.

function listbox1_CreateFcn(hObject, eventdata, handles)

% hObject handle to listbox1 (see GCBO)

% eventdata reserved - to be defined in a future version of MATLAB

% handles empty - handles not created until after all CreateFcns called

% Hint: listbox controls usually have a white background on Windows.

% See ISPC and COMPUTER.

if ispc && isequal(get(hObject,'BackgroundColor'), get(0,'defaultUicontrolBackgroundColor'))

set(hObject,'BackgroundColor','white');

end

function edit4_Callback(hObject, eventdata, handles)

% hObject handle to edit4 (see GCBO)

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA)

% Hints: get(hObject,'String') returns contents of edit4 as text

% str2double(get(hObject,'String')) returns contents of edit4 as a double global nr_mis;

nr_mis = get(handles.edit4,'string');

nr_mis = str2double(nr_mis);

% --- Executes during object creation, after setting all properties.

function edit4_CreateFcn(hObject, eventdata, handles)

% hObject handle to edit4 (see GCBO)

% eventdata reserved - to be defined in a future version of MATLAB

% handles empty - handles not created until after all CreateFcns called

% Hint: edit controls usually have a white background on Windows.

% See ISPC and COMPUTER.

if ispc && isequal(get(hObject,'BackgroundColor'), get(0,'defaultUicontrolBackgroundColor'))

set(hObject,'BackgroundColor','white');

end

(15)

% --- Executes on button press in pushbutton4.

function pushbutton4_Callback(hObject, eventdata, handles)

% hObject handle to pushbutton4 (see GCBO)

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA)

global ARV_EXT ARV_FLEX ARV_PRO RMS_EXT RMS_FLEX RMS_PRO TETA_EXT TETA_FLEX TETA_PRO;

global ARV_AD RMS_AD TETA_AD ARV_AB RMS_AB TETA_AB nr_mis parametro;

axes(handles.axes4);

if strcmp(parametro,'arv') for i=1:nr_mis

plot3(ARV_EXT(i,1), ARV_EXT(i,2), ARV_EXT(i,3),'rs');

hold on

plot3(ARV_FLEX(i,1), ARV_FLEX(i,2), ARV_FLEX(i,3),'ko');

plot3(ARV_PRO(i,1), ARV_PRO(i,2), ARV_PRO(i,3),'*');

plot3(ARV_AD(i,1), ARV_AD(i,2), ARV_AD(i,3),'gd');

plot3(ARV_AB(i,1), ARV_AB(i,2), ARV_AB(i,3),'c+');

hold on

set(handles.axes4,'XMinorTick','on') grid on

saveas(axes4,'grafici.fig');

end hold off

elseif strcmp(parametro,'rms') for i=1:nr_mis

plot3(RMS_EXT(i,1), RMS_EXT(i,2), RMS_EXT(i,3),'rs');

hold on

plot3(RMS_FLEX(i,1), RMS_FLEX(i,2), RMS_FLEX(i,3),'ko');

plot3(RMS_PRO(i,1), RMS_PRO(i,2), RMS_PRO(i,3),'*');

plot3(RMS_AD(i,1), RMS_AD(i,2), RMS_AD(i,3),'gd');

plot3(RMS_AB(i,1), RMS_AB(i,2), RMS_AB(i,3),'c+');

hold on

set(handles.axes4,'XMinorTick','on') grid on

saveas(axes4,'grafici.fig');

end hold off

elseif strcmp(parametro,'teta') for i=1:nr_mis

plot3(TETA_EXT(i,1), TETA_EXT(i,2), TETA_EXT(i,3),'rs');

hold on

plot3(TETA_FLEX(i,1), TETA_FLEX(i,2), TETA_FLEX(i,3),'ko');

plot3(TETA_PRO(i,1), TETA_PRO(i,2), TETA_PRO(i,3),'*');

plot3(TETA_AD(i,1), TETA_AD(i,2), TETA_AD(i,3),'gd');

plot3(TETA_AB(i,1), TETA_AB(i,2), TETA_AB(i,3),'c+');

hold on

set(handles.axes4,'XMinorTick','on') grid on

saveas(axes4,'grafici.fig');

end hold off

else errordlg('Invalid input!!!','ERROR DIALOG BOX','modal');

end

function edit5_Callback(hObject, eventdata, handles)

% hObject handle to edit5 (see GCBO)

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA)

% Hints: get(hObject,'String') returns contents of edit5 as text

% str2double(get(hObject,'String')) returns contents of edit5 as a double

(16)

global parametro

parametro = (get(handles.edit5, 'String'));

% --- Executes during object creation, after setting all properties.

function edit5_CreateFcn(hObject, eventdata, handles)

% hObject handle to edit5 (see GCBO)

% eventdata reserved - to be defined in a future version of MATLAB

% handles empty - handles not created until after all CreateFcns called

% Hint: edit controls usually have a white background on Windows.

% See ISPC and COMPUTER.

if ispc && isequal(get(hObject,'BackgroundColor'), get(0,'defaultUicontrolBackgroundColor'))

set(hObject,'BackgroundColor','white');

end

% --- Executes on button press in pushbutton5.

function pushbutton5_Callback(hObject, eventdata, handles)

% hObject handle to pushbutton5 (see GCBO)

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA)

% Close the GUI and any plot window that is open close(EMGui)

ƒ Matlab function che calcola gli istanti di attivazione, esegue il finestraggio dei segnali calcolando i parametri arv, rms e teta.

% 'C' è l'acquisizione ritenuta buona in fase di calibrazione function [arv rms teta threshold] = win_par(C)

%envC = Inviluppo(C);%calcolo gli inviluppi dei canali

%Calcolo dell' onset.

for j = 1:3

sign = C(:,j);

[sampon soglia] = solonset(sign,1,length(sign));

on(j) = sampon;%creo un vettore degli onset dei tre canali threshold(j) = soglia;%creo un vettore delle soglie

end;

%Calcolo dei teta

if on(1) == 0 || on(2) == 0 tetaon12 = 0;

else tetaon12 = abs(on(1) - on(2));

end;

if on(1) == 0 || on(3) == 0 tetaon13 = 0;

else tetaon13 = abs(on(1) - on(3));

end;

if on(2) == 0 || on(3) == 0 tetaon23 = 0;

else tetaon23 = abs(on(2) - on(3));

end;

%Eseguo il finestraggio.

for n = 1:3

new_C(:,n) = C(on(n):on(n)+1999,n);

end;

%Creazione delle matrici dei parametri arv, rms e teta %[arv rms] = parametri(new_C);

for i = 1:3

par1(:,i) = ARV(new_C(:,i)); %Valore Medio Rettificato par2(:,i) = RMS(new_C(:,i)); %Valore Efficace

(17)

end;

arv = par1;

rms = par2;

teta = [tetaon12 tetaon13 tetaon23];

end

%=========================================================================%

%Questa funzione restituisce, per ogni movimento, le matrici dei 3

%parametri per i tre movimenti, sulle nr_mis misure,(9 matrici):

%

% parametro = [nr_mis x 3 canali]

%

%=========================================================================%

ƒ Matlab function che calcola la matrice dei valori medi e delle deviazioni standard dei paramentri misurati su 20 acquisizioni per ognuno dei 4 movimenti studiati.

function [arvm arvds rmsm rmsds] = calcolapar(par1, par2)

L = length(par1);

%costruisco una matrice [4*nr_mis x 3] con tutti gli arv dei 4 movimenti

%sui 3 canali for i = 1:3 volte = 0;

indice_row = 1;

for j = 1:L

if par1(j,i) ~= 0 volte = 1;

elseif volte == 1

arv(indice_row,i) = par1(j-1,i);

indice_row = indice_row + 1;

volte = 0;

end

end end;

%calcolo la matrice dei valori medi e delle dev.st. x il classificatore

%Simulink di dimensioni [movimenti x canali] (4x3)

for i = 1:3

arvm(1,i) = mean(arv(1:5,i));

arvm(2,i) = mean(arv(6:10,i));

arvm(3,i) = mean(arv(11:15,i));

arvm(4,i) = mean(arv(16:20,i));

arvds(1,i) = std(arv(1:5,i));

arvds(2,i) = std(arv(6:10,i));

arvds(3,i) = std(arv(11:15,i));

arvds(4,i) = std(arv(16:20,i));

end;

M = length(par2);

(18)

%costruisco una matrice [4*nr_mis x 3] con tutti gli rms2 dei 4 movimenti %sui 3 canali

for i = 1:3 volte = 0;

indice_row = 1;

for j = 1:L

if par2(j,i) ~= 0 volte = 1;

elseif volte == 1

rms(indice_row,i) = sqrt(par2(j-1,i));

indice_row = indice_row + 1;

volte = 0;

end

end end;

%calcolo la matrice dei valori medi e delle dev.st. x il classificatore %Simulink di dimensioni [movimenti x canali] (4x3)

for i = 1:3

rmsm(1,i) = mean(rms(1:5,i));

rmsm(2,i) = mean(rms(6:10,i));

rmsm(3,i) = mean(rms(11:15,i));

rmsm(4,i) = mean(rms(16:20,i));

rmsds(1,i) = std(rms(1:5,i));

rmsds(2,i) = std(rms(6:10,i));

rmsds(3,i) = std(rms(11:15,i));

rmsds(4,i) = std(rms(16:20,i));

end;

end

ƒ Matlab function per la costruzione e visualizzazione delle classi CUBE nello spazio dei canali.

function [] = calcolaclassi(vmedi,devst,k)

%plottaggio delle classi figure;

grid on hold on

%costruzione della matrice dei vertici ext1m_min = vmedi(1,1) - k*devst(1,1);

ext1m_max = vmedi(1,1) + k*devst(1,1);

ext2m_min = vmedi(1,2) - k*devst(1,2);

ext2m_max = vmedi(1,2) + k*devst(1,2);

ext3m_min = vmedi(1,3) - k*devst(1,3);

ext3m_max = vmedi(1,3) + k*devst(1,3);

vertici_ext = [ext1m_max ext2m_max ext3m_min;ext1m_min ext2m_max

ext3m_min;ext1m_min ext2m_min ext3m_min;ext1m_max ext2m_min ext3m_min;ext1m_max

(19)

ext2m_max ext3m_max;ext1m_min ext2m_max ext3m_max ;ext1m_min ext2m_min ext3m_max;ext1m_max ext2m_min ext3m_max];

connessioni_ext = [1 2 6 5;2 3 7 6;3 4 8 7;4 1 5 8;1 2 3 4;5 6 7 8];

patch('Vertices',vertici_ext,'Faces',connessioni_ext);

flex1m_min = vmedi(2,1) - k*devst(2,1);

flex1m_max = vmedi(2,1) + k*devst(2,1);

flex2m_min = vmedi(2,2) - k*devst(2,2);

flex2m_max = vmedi(2,2) + k*devst(2,2);

flex3m_min = vmedi(2,3) - k*devst(2,3);

flex3m_max = vmedi(2,3) + k*devst(2,3);

vertici_flex = [flex1m_max flex2m_max flex3m_min;flex1m_min flex2m_max flex3m_min;flex1m_min flex2m_min flex3m_min;flex1m_max flex2m_min

flex3m_min;flex1m_max flex2m_max flex3m_max;flex1m_min flex2m_max

flex3m_max;flex1m_min flex2m_min flex3m_max;flex1m_max flex2m_min flex3m_max];

connessioni_flex = [1 2 6 5;2 3 7 6;3 4 8 7;4 1 5 8;1 2 3 4;5 6 7 8];

patch('Vertices',vertici_flex,'Faces',connessioni_flex);

add1m_min = vmedi(3,1) - k*devst(3,1);

add1m_max = vmedi(3,1) + k*devst(3,1);

add2m_min = vmedi(3,2) - k*devst(3,2);

add2m_max = vmedi(3,2) + k*devst(3,2);

add3m_min = vmedi(3,3) - k*devst(3,3);

add3m_max = vmedi(3,3) + k*devst(3,3);

vertici_add = [add1m_max add2m_max add3m_min;add1m_min add2m_max

add3m_min;add1m_min add2m_min add3m_min;add1m_max add2m_min add3m_min;add1m_max add2m_max add3m_max;add1m_min add2m_max add3m_max;add1m_min add2m_min

add3m_max;add1m_max add2m_min add3m_max];

connessioni_add = [1 2 6 5;2 3 7 6;3 4 8 7;4 1 5 8;1 2 3 4;5 6 7 8];

patch('Vertices',vertici_add,'Faces',connessioni_add);

abd1m_min = vmedi(4,1) - k*devst(4,1);

abd1m_max = vmedi(4,1) + k*devst(4,1);

abd2m_min = vmedi(4,2) - k*devst(4,2);

abd2m_max = vmedi(4,2) + k*devst(4,2);

abd3m_min = vmedi(4,3) - k*devst(4,3);

abd3m_max = vmedi(4,3) + k*devst(4,3);

vertici_abd = [abd1m_max abd2m_max abd3m_min;abd1m_min abd2m_max

abd3m_min;abd1m_min abd2m_min abd3m_min;abd1m_max abd2m_min abd3m_min;abd1m_max abd2m_max abd3m_max;abd1m_min abd2m_max abd3m_max;abd1m_min abd2m_min

abd3m_max;abd1m_max abd2m_min abd3m_max];

connessioni_abd = [1 2 6 5;2 3 7 6;3 4 8 7;4 1 5 8;1 2 3 4;5 6 7 8];

patch('Vertices',vertici_abd,'Faces',connessioni_abd);

%hold off end

(20)

ƒ Embedded Matlab function che implementa il filtro di Kalman per il modello Simulink di

“Calibrazione” e “Real-Time Classification”.

function [stima, reale, varianzaposteriori,varianzapriori, stimafutura] = fcn(in, i1,i2)

PHI = [1 0 0; 0 1 0; 0 0 1];

Q = 0.0001 * [0.3299 -0.1645 -0.0188; -0.1645 0.3392 0.0186; -0.0188 0.0186 0.2193];%matrice di covarianza di processo, scelta considerando il caso peggiore

R = 0.1.*[1 0 0; 0 1 0; 0 0 1];

C = [1 0 0; 0 1 0; 0 0 1];

Xr =in; %ingresso

X = i1; %stima a priori Pp=i2; % varianza a priori

% Calcolo della matrice di guadagno del filtro di Kalman K = Pp * C' * inv(C * Pp * C' + R); % costante kalman [Z, Xr] = Processo(Xr);

% Aggiornamento della stima dello stato

Xn = X + K * (Z - C * X); % stima a posteriori

% Aggiornamento della varianza dei disturbi sullo stato e aggiornamento del ciclo

P = (eye(3) - K * C)* Pp; % stima a posteriori

% Aggiornamento dello stato

Xp = PHI * Xn; %stima dello stato futuro a k+1 stima a priori

% Aggiornamento della stima della varianza dell'errore sullo stato k+1 Pk = PHI * P * PHI' + Q; %stima a priori

stima=Xn;

reale =Xr;

varianzapriori=Pk; % varianza a priori

varianzaposteriori=P; % varianza a posteriori stimafutura=Xp;

function [Z, Xr] = Processo(Xr)

(21)

x1 = Xr;

%x1= x1;%+0.1*randn;

Z = x1 ; % misura dell stato x1

ƒ S-Function Matlab che implementa l’elaborazione per l’inizializzazione del clasificatore nel modello Simulink “Calibrazione”.

Spazio delle variabili di stato:

xD[0] = xD[0] + 1;

//

if (xD[0] >= 3000) {

if (xD[5] == 2000 && xD[10] == 2000 && xD[15] == 2000) {

xD[5] = 51; //riinizializzo le finestre xD[10] = 51;

xD[15] = 51;

xD[1] = 0; //azzero i contatori dei varchi xD[6] = 0;

xD[11] = 0;

xD[2] = 0; //azzero il blocco della ricerca degli onset xD[7] = 0;

xD[12] = 0;

xD[3] = 0; //azzero gli arv xD[8] = 0;

xD[13] = 0;

xD[4] = 0; //azzero gli rms2 xD[9] = 0;

xD[14] = 0;

} else {

if (xD[2] == 0) {

if (canale[0] >= soglia[0]) {

xD[1] = xD[1] + 1;

xD[3] = canale[0] + xD[3];

xD[4] = (canale[0]*canale[0]) + xD[4];

if (xD[1] == 50) {

xD[16]=xD[0] - 49;

xD[2] = 1;

} }

else {

xD[1] = 0;

xD[3] = 0;

xD[4] = 0;

} }

if (xD[1] == 50 && xD[0] < xD[16] + 1998) {

xD[5] = xD[5] + 1;

(22)

xD[3] = canale[0] + xD[3];

xD[4] = (canale[0]*canale[0]) + xD[4];

}

//

if (xD[7] == 0) {

if (canale[1] >= soglia[1]) {

xD[6] = xD[6] + 1;

xD[8] = canale[1] + xD[8];

xD[9] = (canale[1]*canale[1]) + xD[9];

if (xD[6] == 50) {

xD[17]=xD[0] - 49;

xD[7] = 1;

} }

else {

xD[6] = 0;

xD[8] = 0;

xD[9] = 0;

} }

if (xD[6] == 50 && xD[0] < xD[17] + 1998) {

xD[10] = xD[10] + 1;

xD[8] = canale[1] + xD[8];

xD[9] = (canale[1]*canale[1]) + xD[9];

} //

if (xD[12] == 0) {

if (canale[2] >= soglia[2]) {

xD[11] = xD[11] + 1;

xD[13] = canale[2] + xD[13];

xD[14] = (canale[2]*canale[2]) + xD[14];

if (xD[11] == 50) {

xD[18]=xD[0] - 49;

xD[12] = 1;

} }

else {

xD[11] = 0;

xD[13] = 0;

xD[14] = 0;

} }

if (xD[11] == 50 && xD[0] < xD[18] + 1998) {

xD[15] = xD[15] + 1;

xD[13] = canale[2] + xD[13];

xD[14] = (canale[2]*canale[2]) + xD[14];

} } }

(23)

Spazio degli outputs:

//

onset[0] = xD[16];

arv[0]=xD[3]/2000;

rms2[0]=xD[4]/2000;

finestra[0] = xD[5];

//

onset[1] = xD[17];

arv[1]=xD[8]/2000;

rms2[1]=xD[9]/2000;

finestra[1] = xD[10];

//

onset[2] = xD[18];

arv[2]=xD[13]/2000;

rms2[2]=xD[14]/2000;

finestra[2] = xD[15];

ƒ S-Funcion Matlab per la classificazione in tempo reale e il controllo del cursore su schermo del modello Simulink “Real-Time Application”.

NOTA: lo spazio delle variabili di stato è identico al listato precedente.

Spazio degli outputs:

onset[0] = xD[16];

arv[0]=xD[3]/2000;

rms2[0]=xD[4]/2000;

finestra[0] = xD[5];

onset[1] = xD[17];

arv[1]=xD[8]/2000;

rms2[1]=xD[9]/2000;

finestra[1] = xD[10];

onset[2] = xD[18];

arv[2]=xD[13]/2000;

rms2[2]=xD[14]/2000;

finestra[2] = xD[15];

if (xD[5]==2000 && xD[10]==2000 && xD[15]==2000) {

if (((fabs(arv[0]-arvm[0])<=3*arvst[0]) && (fabs(arv[1]- arvm[4])<=3*arvst[4]) && (fabs(arv[2]-arvm[8])<=3*arvst[8])) ||

((fabs(sqrt(rms2[0])-rmsm[0])<= 3*rmsst[0]) && (fabs(sqrt(rms2[1])-rmsm[4])<=

3*rmsst[4]) && (fabs(sqrt(rms2[2])-rmsm[8])<= 3*rmsst[8]))) {

y[0]= y[0]+1;

}

if (((fabs(arv[0]-arvm[3])<=5*arvst[3]) && (fabs(arv[1]- arvm[7])<=5*arvst[7]) && (fabs(arv[2]-arvm[11])<=5*arvst[11])) ||

((fabs(sqrt(rms2[0])-rmsm[3])<= 5*rmsst[3]) && (fabs(sqrt(rms2[3])-rmsm[7])<=

5*rmsst[7]) && (fabs(sqrt(rms2[2])-rmsm[11])<= 5*rmsst[11]))) {

x[0] = x[0]+1;

}

(24)

if (((fabs(arv[0]-arvm[1])<=4*arvst[1]) && (fabs(arv[1]- arvm[5])<=4*arvst[5]) && (fabs(arv[2]-arvm[9])<=4*arvst[9])) ||

((fabs(sqrt(rms2[0])-rmsm[1])<= 4*rmsst[1]) && (fabs(sqrt(rms2[1])-rmsm[5])<=

4*rmsst[5]) && (fabs(sqrt(rms2[2])-rmsm[9])<= 4*rmsst[9]))) {

y[0] = y[0]-1;

}

if (((fabs(arv[0]-arvm[2])<=3*arvst[2]) && (fabs(arv[1]- arvm[6])<=3*arvst[6]) && (fabs(arv[2]-arvm[10])<=3*arvst[10])) ||

((fabs(sqrt(rms2[0])-rmsm[2])<= 3*rmsst[2]) && (fabs(sqrt(rms2[1])-rmsm[6])<=

3*rmsst[6]) && (fabs(sqrt(rms2[2])-rmsm[10])<= 3*rmsst[10]))) {

x[0] = x[0]-1;

} }

ƒ Matlab function per il test di cross validation del classificatoreCUBE.

%miomatdati = matrice dei dati [80x7], dove 7 sono le features ( i 3 ARV e i

%tre RMS), l'ultima colonna sono le classi, e 80 sono gli 'esempi', ovvero le 20 acquisizioni per ogni classe

%(movimento).

%==========================================================================

%scelta del numero di esempi da usare come training e di quelli da usare

%come test.

numesempitrain = input('Inserisci quanti esempi vuoi per il training: da 1 a 19 '); %esempi per il training.

numesempitest = 20 - numesempitrain; %esempi per il test.

%%%%

box = confusMatrixStatInit(4); %inizializzazione della struttura confusMatrixStat.

%%%%

%CICLO DI CROSS VALIDATION for n = 1:20

%Estrazione dal miomatdati dei numesempitrain in maniera casuale.

index1 = randperm(20); %vettore riga di 20 numeri da 1 a 20 in ordine casuale.

for i = 1:20

dataset1(i,:) = miomatdati(index1(i),:);

end

index2 = randperm(20)+20;

for i = 1:20

dataset2(i,:) = miomatdati(index2(i),:);

(25)

end

index3 = randperm(20)+40;

for i = 1:20

dataset3(i,:) = miomatdati(index3(i),:);

end

index4 = randperm(20)+60;

for i = 1:20

dataset4(i,:) = miomatdati(index4(i),:);

end;

%Creazione della matrice dati per il training del classificatore 'cube':

[numesempitrain x 7].

datatrain = [dataset1(1:numesempitrain,:); dataset2(1:numesempitrain,:);

dataset3(1:numesempitrain,:); dataset4(1:numesempitrain,:)];

%Creazione della matrice dati per il test del classificatore 'cube':

[numesempitest x 7].

datatest = [dataset1(numesempitrain+1:end,:); dataset2(numesempitrain+1:end,:);

dataset3(numesempitrain+1:end,:); dataset4(numesempitrain+1:end,:)];

%Calcolo dei parametri per il classificatore dal datatrain: [4 x 6].

vmedi = [mean(datatrain(1:numesempitrain,1:end-1));

mean(datatrain(numesempitrain+1:2*numesempitrain,1:end-1));

mean(datatrain(2*numesempitrain+1:3*numesempitrain,1:end-1));

mean(datatrain(3*numesempitrain+1:4*numesempitrain,1:end-1))];

devst = [std(datatrain(1:numesempitrain,1:end-1));

std(datatrain(numesempitrain+1:2*numesempitrain,1:end-1));

std(datatrain(2*numesempitrain+1:3*numesempitrain,1:end-1));

std(datatrain(3*numesempitrain+1:4*numesempitrain,1:end-1))];

%%%%%%%%%%%%%

confusione = cubeclass(datatest, numesempitest, vmedi,devst, 2,2,2,2); %calcolo della matrice di confusione

box = confusMatrixStatAdd(box, confusione(:,1:4)); %calcolo delle statistiche di CROSS VALIDATION

end;

%%%%%%%%%%%%%

[boxMean, boxStd] = confusMatrixStatGet(box); %estraggo dalla struttura le matrici MEAN e STD sulle 10 mat di conf.

(26)

ƒ Matlab function per il test di classificazione e per la costruzione della matrice di confusione del test.

function [confusmat] = cubeclass(datatest, numesempitest, vmedi, devst, k1, k2, k3, k4)

%La funzione svolge le seguenti operazioni:

%

% 1) Test di classificazione col datatest fornito.

%

% 2) Construzione della matrice di confusione per il

% test.

%

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

%%%% %%%%

%%%% PROCEDURA DI CLASSIFICAZIONE %%%%

%%%% %%%%

confusmat = zeros(4,5); %inizializzo la matrice di confusione: sulla colonna 5 i NON CLASSIFICATI in alcuna delle 4 classi.

for i = 1:4*numesempitest

confusprec = confusmat;

%%%%%BLOCCO ESTENSIONE

if ((abs(datatest(i,1) - vmedi(1,1))<= k1*devst(1,1)) && (abs(datatest(i,2) - vmedi(1,2))<= k1*devst(1,2)) && (abs(datatest(i,3) - vmedi(1,3))<=

k1*devst(1,3))) || ((abs(datatest(i,4) - vmedi(1,4))<= k1*devst(1,4)) &&

(abs(datatest(i,5) - vmedi(1,5))<= k1*devst(1,5)) && (abs(datatest(i,6) - vmedi(1,6))<= k1*devst(1,6)))

if datatest(i,end) == 1; % riconoscimento esatto dell'EXT.

confusmat(1,1) = confusmat(1,1) + 1; %aggiornamento della matrice di confusione.

elseif datatest(i,end) == 2; % scambio con la FLEX.

confusmat(1,2) = confusmat(1,2) + 1; %aggiornamento della matrice di confusione.

elseif datatest(i,end) == 3; % scambio con la ADD.

confusmat(1,3) = confusmat(1,3) + 1; %aggiornamento della matrice di confusione.

elseif datatest(i,end) == 4; % scambio con la ABD.

confusmat(1,4) = confusmat(1,4) + 1; %aggiornamento della matrice di confusione.

end;

end;

(27)

%%%%%BLOCCO FLESSIONE

if ((abs(datatest(i,1) - vmedi(2,1))<= k2*devst(2,1)) && (abs(datatest(i,2) - vmedi(2,2))<= k2*devst(2,2)) && (abs(datatest(i,3) - vmedi(2,3))<=

k2*devst(2,3))) || ((abs(datatest(i,4) - vmedi(2,4))<= k2*devst(2,4)) &&

(abs(datatest(i,5) - vmedi(2,5))<= k2*devst(2,5)) && (abs(datatest(i,6) - vmedi(2,6))<= k2*devst(2,6)))

if datatest(i,end) == 1; % scambio con l'EXT.

confusmat(2,1) = confusmat(2,1) + 1; %aggiornamento della matrice di confusione.

elseif datatest(i,end) == 2; % riconoscimento esatto della FLEX.

confusmat(2,2) = confusmat(2,2) + 1; %aggiornamento della matrice di confusione.

elseif datatest(i,end) == 3; % scambio con la ADD.

confusmat(2,3) = confusmat(2,3) + 1; %aggiornamento della matrice di confusione.

elseif datatest(i,end) == 4; % scambio con la ABD.

confusmat(2,4) = confusmat(2,4) + 1; %aggiornamento della matrice di confusione.

end;

end;

%%%%%BLOCCO ADDUZIONE

if ((abs(datatest(i,1) - vmedi(3,1))<= k3*devst(3,1)) && (abs(datatest(i,2) - vmedi(3,2))<= k3*devst(3,2)) && (abs(datatest(i,3) - vmedi(3,3))<=

k3*devst(3,3))) || ((abs(datatest(i,4) - vmedi(3,4))<= k3*devst(3,4)) &&

(abs(datatest(i,5) - vmedi(3,5))<= k3*devst(3,5)) && (abs(datatest(i,6) - vmedi(3,6))<= k3*devst(3,6)))

if datatest(i,end) == 1; % scambio con l'EXT.

confusmat(3,1) = confusmat(3,1) + 1; %aggiornamento della matrice di confusione.

elseif datatest(i,end) == 2; % scambio con la FLEX.

confusmat(3,2) = confusmat(3,2) + 1; %aggiornamento della matrice di confusione.

elseif datatest(i,end) == 3; % riconoscimento esatto della ADD.

confusmat(3,3) = confusmat(3,3) + 1; %aggiornamento della matrice di confusione.

(28)

elseif datatest(i,end) == 4; % scambio con la ABD.

confusmat(3,4) = confusmat(3,4) + 1; %aggiornamento della matrice di confusione.

end;

end;

%%%%%BLOCCO ABDUZIONE

if ((abs(datatest(i,1) - vmedi(4,1))<= k4*devst(4,1)) && (abs(datatest(i,2) - vmedi(4,2))<= k4*devst(4,2)) && (abs(datatest(i,3) - vmedi(4,3))<=

k4*devst(4,3))) || ((abs(datatest(i,4) - vmedi(4,4))<= k4*devst(4,4)) &&

(abs(datatest(i,5) - vmedi(4,5))<= k4*devst(4,5)) && (abs(datatest(i,6) - vmedi(4,6))<= k4*devst(4,6)))

if datatest(i,end) == 1; % scambio con l'EXT.

confusmat(4,1) = confusmat(4,1) + 1; %aggiornamento della matrice di confusione.

elseif datatest(i,end) == 2; % scambio con la FLEX.

confusmat(4,2) = confusmat(4,2) + 1; %aggiornamento della matrice di confusione.

elseif datatest(i,end) == 3; % scambio con la ADD.

confusmat(4,3) = confusmat(4,3) + 1; %aggiornamento della matrice di confusione.

elseif datatest(i,end) == 4; % riconoscimento esatto della ABD.

confusmat(4,4) = confusmat(4,4) + 1; %aggiornamento della matrice di confusione.

end;

end;

%%%%BLOCCO DI NON CLASSIFICAZIONE

if confusmat(:,1:4) == confusprec (:,1:4)

if datatest(i,end) == 1; %EXT.

confusmat(1,5) = confusmat(1,5) + 1;

elseif datatest(i,end) == 2; %FLEX.

confusmat(2,5) = confusmat(2,5) + 1;

(29)

elseif datatest(i,end) == 3; %ADD.

confusmat(3,5) = confusmat(3,5) + 1;

elseif datatest(i,end) == 4; %ABD.

confusmat(4,5) = confusmat(4,5) + 1;

end end;

end; %finito il ciclo ho completato la matrice di confusione.

confusmat = [confusmat/numesempitest]; %normalizzazione dellla matrice di confusione.

end

ƒ Strutture Matlab per la gestione del test di cross validation.

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

%

% [ confusStat ] = confusMatrixStatInit(numClasses)

%

function [ confusStat ] = confusMatrixStatInit(numClasses)

confusStat.data = [];

confusStat.classes = numClasses;

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

%

% [ confusStat ] = confusMatrixStatAdd(confusStat, confus)

%

function [ confusStat ] = confusMatrixStatAdd(confusStat, confus) r = confusStat.classes;

row = [];

for i=1:r

row = [ row, confus(i,:) ];

end

confusStat.data = [ confusStat.data; row ];

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

%

% [ confusMean, confusStd ] = confusMatrixStatGet(confusStat)

%

(30)

function [ confusMean confusStd ] = confusMatrixStatGet(confusStat) r = confusStat.classes;

cMean = mean(confusStat.data);

cStd = std(confusStat.data);

confusMean = [];

confusStd = [];

for i=1:r

confusMean = [ confusMean; cMean( ((i-1)*r+1):((i-1)*r+r) ) ];

confusStd = [ confusStd; cStd( ((i-1)*r+1):((i-1)*r+r) ) ];

end

ƒ Matlab GUI per la gestione della precalibrazione, della calibrazione e dell’applicazione real- time di classificazione e controllo cursore.

function varargout = EMGui1(varargin)

% EMGUI1 M-file for EMGui1.fig

% EMGUI1, by itself, creates a new EMGUI1 or raises the existing

% singleton*.

%

% H = EMGUI1 returns the handle to a new EMGUI1 or the handle to

% the existing singleton*.

%

% EMGUI1('CALLBACK',hObject,eventData,handles,...) calls the local

% function named CALLBACK in EMGUI1.M with the given input arguments.

%

% EMGUI1('Property','Value',...) creates a new EMGUI1 or raises the

% existing singleton*. Starting from the left, property value pairs are

% applied to the GUI before EMGui1_OpeningFcn gets called. An

% unrecognized property name or invalid value makes property application

% stop. All inputs are passed to EMGui1_OpeningFcn via varargin.

%

% *See GUI Options on GUIDE's Tools menu. Choose "GUI allows only one

% instance to run (singleton)".

%

% See also: GUIDE, GUIDATA, GUIHANDLES

% Edit the above text to modify the response to help EMGui1

% Last Modified by GUIDE v2.5 28-May-2008 18:50:57

% Begin initialization code - DO NOT EDIT gui_Singleton = 1;

gui_State = struct('gui_Name', mfilename, ...

'gui_Singleton', gui_Singleton, ...

'gui_OpeningFcn', @EMGui1_OpeningFcn, ...

'gui_OutputFcn', @EMGui1_OutputFcn, ...

'gui_LayoutFcn', [] , ...

'gui_Callback', []);

if nargin && ischar(varargin{1})

gui_State.gui_Callback = str2func(varargin{1});

end

if nargout

[varargout{1:nargout}] = gui_mainfcn(gui_State, varargin{:});

else

(31)

gui_mainfcn(gui_State, varargin{:});

end

% End initialization code - DO NOT EDIT

% --- Executes just before EMGui1 is made visible.

function EMGui1_OpeningFcn(hObject, eventdata, handles, varargin)

% This function has no output args, see OutputFcn.

% hObject handle to figure

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA)

% varargin command line arguments to EMGui1 (see VARARGIN)

% Choose default command line output for EMGui1 handles.output = hObject;

% Update handles structure guidata(hObject, handles);

% UIWAIT makes EMGui1 wait for user response (see UIRESUME)

% uiwait(handles.figure1);

Calibrazione2; %apre il modello Simulink per la calibrazione pause(1);

set_param('Calibrazione2/soglie','Value','[0 0 0]');%inizializzo le soglie rtwbuild('Calibrazione2');% esegue il "build"

pause(1);

global arvm arvds rmsm rmsds;global threshold;

arvm=[]; arvds=[]; rmsm=[]; rmsds=[];threshold =[];

% --- Outputs from this function are returned to the command line.

function varargout = EMGui1_OutputFcn(hObject, eventdata, handles)

% varargout cell array for returning output args (see VARARGOUT);

% hObject handle to figure

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA)

% Get default command line output from handles structure varargout{1} = handles.output;

% --- Executes on button press in pushbutton1.

function pushbutton1_Callback(hObject, eventdata, handles)

% hObject handle to pushbutton1 (see GCBO)

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA)

set_param('Calibrazione2','SimulationCommand','Connect');

pause(2.5);

set_param('Calibrazione2','SimulationCommand','Start');

% --- Executes on button press in pushbutton2.

function pushbutton2_Callback(hObject, eventdata, handles)

% hObject handle to pushbutton2 (see GCBO)

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA) global arvm arvds rmsm rmsds;

set_param('Calibrazione2','SimulationCommand','Stop');%termina l'acquisizione

(32)

pause(1);%aspetta

set_param('Calibrazione2','SimulationCommand','Disconnect'); %disconnette il modulo simulink dal target

%fase di elaborazione

ARV = evalin('base','arv');%prelevo dal workspace le variabili salvate dalla fase di acquisizione

RMS2 = evalin('base','rms2');

[arvm arvds rmsm rmsds] = calcolapar(ARV,RMS2);%funzione che calcola le matrici di calibrazione per il classificatore

%per verifica salvo le matrici [4x3]

save ARVM arvm;

save ARVDS arvds;

save RMSM rmsm;

save RMSDS rmsds;

save pararv ARV;

save parrms2 RMS2;

SEGNALI = evalin('base','ScopeData');

save ScopeData SEGNALI;

% --- Executes on button press in pushbutton3.

function pushbutton3_Callback(hObject, eventdata, handles)

% hObject handle to pushbutton3 (see GCBO)

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA)

global arvm arvds rmsm rmsds;global threshold;

Realtime7; %apro il modello Simulink x la classificazione pause(1);

%inizializzo le matrici di calibrazione per il classificatore e le soglie

set_param('Realtime7/arvm','Value',['[',num2str(arvm(1,:)),';',num2str(arvm(2,:) ),';',num2str(arvm(3,:)),';',num2str(arvm(4,:)),']']);

set_param('Realtime7/arvst','Value',['[',num2str(arvds(1,:)),';',num2str(arvds(2 ,:)),';',num2str(arvds(3,:)),';',num2str(arvds(4,:)),']']);

set_param('Realtime7/rmsm','Value',['[',num2str(rmsm(1,:)),';',num2str(rmsm(2,:) ),';',num2str(rmsm(3,:)),';',num2str(rmsm(4,:)),']']);

set_param('Realtime7/rmsst','Value',['[',num2str(rmsds(1,:)),';',num2str(rmsds(2 ,:)),';',num2str(rmsds(3,:)),';',num2str(rmsds(4,:)),']']);

set_param('Realtime7/soglie','Value',['[',num2str(threshold),']']);

%set_param('Realtime7/soglie','Value','[0.015 0.015 0.02]');

rtwbuild('Realtime7');% esegue il "build"

pause(1);

%inizio l'acquisizione

set_param('Realtime7','SimulationCommand','Connect');

pause(2.5);

set_param('Realtime7','SimulationCommand','Start');

% --- Executes on button press in pushbutton4.

function pushbutton4_Callback(hObject, eventdata, handles)

% hObject handle to pushbutton4 (see GCBO)

% eventdata reserved - to be defined in a future version of MATLAB

% handles structure with handles and user data (see GUIDATA) global threshold;

%Precalibrazione

%acquisisco rumore per circa 8s

set_param('Calibrazione2','SimulationCommand','Connect');%avvia l'acquisizione pause(1);

(33)

set_param('Calibrazione2','SimulationCommand','Start');

pause(8)

set_param('Calibrazione2','SimulationCommand','Stop');%termina l'acquisizione pause(1);

set_param('Calibrazione2','SimulationCommand','Disconnect');%disconnette il modulo simulink

signal = evalin('base','ScopeData');%prelevo dal workspace il segnale acquisito come inviluppo

C = Sep_Rett(signal);%nella matrice C ho i 3 canali utili senza il tempo

%calcolo delle soglie dei canali su 2000smps for i = 1:3

sign = C(:,i);

threshold(i) = mean(sign(3000:6000)) + 5*std(sign(3000:6000));

end;

set_param('Calibrazione2/soglie','Value',['[',num2str(threshold),']']);

rtwbuild('Calibrazione2');% esegue il "build"

Riferimenti

Documenti correlati

• Regola 3: Anche se le stringhe di formato della scanf() assomigliano molto a quelle della printf(), hanno una semantica leggermente differente (leggete il manuale!). • Regola

By default, each function and data file will use a different line type and point type, up to the maximum number of available types. All terminal drivers support at least six

Per aprire uno stream di output occorre dichiarare che appartiene alla classe ofstream: ofstream out;.. Uno stream che eseguirà operazioni di input ed output deve appartenere

Indeed, by default I-DLV output is produced in a numeric format compliant with the mentioned solvers.. In order to interoperate with a

whose name is distinct from all other existing files, and opens the file for binary writing and reading (as if the mode string &#34;wb+&#34; were used in an fopen() call). If

© 2000 Pier Luca Montessoro (si veda la nota di copyright alla slide n. 2) 2 Questo insieme di trasparenze (detto nel seguito slide) è protetto dalle leggi sul copyright e

Si osserva che, pur essendo tutti gli autovalori di B inclusi nell’intervallo [10 −6 , 10 −2 ], ed essendo massimo il rango della matrice (pari alla dimensione della matrice),

Il contenuto della parentesi che seguono l'istruzione writeln può essere sia un'espressione (stringa o numerica), sia una variabile sia una combinazione. La parte testuale è