Laboratorul 02.

Semnale şi sisteme de bază

La curs am discutat despre semnale de bază şi sisteme. În continuare vom face câteva exerciţii legate de aceste noţiuni.

Exerciţiul 1 [2p]

Pentru a transmite simboluri (ex: litere din alfabet) modemurile PC-urilor folosesc două frecvenţe (1600 Hz şi 1800 Hz) şi mai multe niveluri de amplitudine. O transmisiune se face într-o perioadă de timp T (interval de transmisie) şi este egală cu suma a două semnale de amplitudine diferită:

x(t) = A1 * sin (2*pi*f1*t) + A2 * sin (2*pi*f2*t)

  1. Care este cel mai mic interval de transmisie care are sens să fie folosit cu frecvenţele de mai sus? Cu alte cuvinte, cât ar trebui să fie T astfel încât semnalul să aibă un număr întreg de cicluri? [1p]
  2. Afişaţi cu ajutorul Matlab semnalul produs de modem pe parcursul mai multor intervale de transmisie consecutive. Aşa cum am învăţat în laboratorul trecut adăugaţi titlu şi etichete plotului. [1p]

Prima frecvenţă este de 1600 = 8 * 200 Hz, iar a doua de 1800 = 9 * 200 Hz. Este clar că amândouă sunt multiple de 200 Hz. Astfel, dacă folosim o frecvenţă de 200 Hz ( T = 1/200 s ), primul semnal va cicla de 8 ori, iar al doilea de 9 ori. De aceea avem nevoie de o perioadă minimă de T = 1/200.

Un posibil cod de afişare a semnalului:

'sinewaves.m'
%% Sinewaves
close all;
f1 = 1800;
f2 = 1600;
fm = 200;
tm = 1/fm;
x = 0:tm/100:tm;
s1 = sin(2*pi*f1*x);
s2 = sin(2*pi*f2*x);
h1 = figure;
plot(x, [s1; s2]);
xlabel('Time (s)');
ylabel('Amplitude');
title('Two sinewaves');
legend('1800 Hz', '1600 Hz');
print(h1, '-dpng', 'sines.png');

Exerciţiul 2 [2.5p]

La curs am văzut că putem descompune semnalele într-o sumă de mai multe semnale de bază (ramp, step etc.). Pentru acest exerciţiu veţi încerca să folosiţi semnalele 'step' şi 'ramp' pentru a crea semnalul reprezentat cu negru în acest slide: building_signals.pdf

Pentru a face asta în Matlab va trebui să lucrăm cu semnale discrete, nu continue (vom discuta despre acest aspect în cursurile viitoare). În loc să lucrăm cu semnale reprezentate in intervalul [0,1] ca în slide vom folosi semnale ce se întind peste 100 de puncte.

Puteţi folosi următoarea funcţie pentru a crea un semnal 'ramp' peste N puncte:

ramp.m
function y=ramp(N)
%RAMP Returns a ramp signal of a given number of samples
%   [y] = RAMP(N)
%   returns the ramp signal for the given samples
 
y = zeros(1, N);
for t=1:N
    y(t) = t-1;
end

Task-ul vostru este să creaţi un semnal combinat, ca cel din slide, dar folosind secvenţe discrete, cu o formulă ca cea de mai jos:

s(i) = r(i) - r(i-T) - T*u(i-T)

unde i este un index de la 0 la N (în loc de un număr real de la 0 la 1), T este întârzierea, s este semnalul rezultat, r este semnalul 'ramp' (eventual întârziat cu T) şi u este semnalul 'unit step' (întârziat aici cu T).

  • r(i-T) este doar o notaţie care marchează faptul că folosim un semnal 'ramp' întârziat cu T. Nu trebuie să apelaţi funcţia ramp cu argumentul (i-T) pentru că nu va funcţiona. Va trebui să întârziaţi semnalul 'de mână' ca mai jos.
  • Folosim factorul T în faţa lui u(i-T) pentru că este amplitudinea la care r(i) a ajuns până în acel moment şi vrem să avem semnalul final la 0.

Pentru asta ar trebui să:

  1. creaţi un semnal 'unit step' numit ustep.m, care practic întoarce o secvenţă de N valori de 1 [0.5p]
  2. să setaţi numărul de puncte la N = 200 şi delay-ul la T = 100
  3. să creaţi cele 3 semnale (care urmează să fie combinate) folosind 'ramp' şi 'ustep' cu N şi T de mai sus. [1p]
    • Puteţi crea secvenţa de input ca:
       x=1:N; 
    • Puteţi crea primul semnal ca:
       s1 = ramp(N) 
    • Puteţi întârzia un semnal cu T în felul următor:
       [zeros(1,T), s(1:N-T)]; 
  4. combinaţi cele 3 semnale
  5. afişaţi toate cele 4 semnale (cele 3 individuale şi combinaţia lor) [1p]
    • folosiţi culori diferite (eventual grosimi de linie diferite) pentru fiecare semnal şi afişaţi legenda pentru a diferenţia semnalele.

Folosiţi 'help plot' sau 'doc plot' pentru a vedea cum se plotează un semnal. De exemplu pentru a plota s1 cu o linie verde de grosime 2 puteţi folosi codul următor:

 plot(x, s1, 'g-', 'LineWidth', 2); 

Pentru a afişa mai multe semnale în aceeaşi figură cu ajutorul comenzii plot puteţi folosi

 hold on; 

după primul plot:

figure;
plot(x, s1, 'g-', 'LineWidth', 2);
hold on;
plot(...)

Ar trebui să obtineţi ceva similar imaginii de mai jos:

Acesta este codul pentru funcţia 'unit step':

ustep.m
function y=ustep(N)
%RAMP Returns a step signal of a given number of smaples
%   [y] = USTEP(N)
%   returns the step signal for the given samples
 
y = ones(1, N);

Pentru a combina ploturile puteţi folosi următorul cod:

signal_composition.m
N = 200;
T = 100;
y1 = ramp(N);
y2 = [zeros(1,T), -y1(1:N-T)];
y3 = ustep(N);
y3 = [zeros(1,T), -T*y3(1:N-T)];
ys = y1+y2+y3;
x = 1:N;
s1 = y1(x);
s2 = y2(x);
s3 = y3(x);
ss = s1+s2+s3;
h = figure;
plot(x, ss, 'k-', 'LineWidth', 3);
hold on;
plot(x, s1, 'g-', 'LineWidth', 2);
plot(x, s2, 'b-', 'LineWidth', 2);
plot(x, s3, 'r-', 'LineWidth', 2);
legend('sum', 'r(t)', '-r(t-T)', '-u(t-T)');
print(h1, '-dpng', 'combined_signals.png');

Exerciţiul 3 [1p]

La curs am văzut că datorită egalității lui Euler putem scrie o exponenţială complexă ca o sumă de sin şi cos:

$e^{j\cdot t} = \cos(t) + j\cdot \sin(t)$

De asemenea:

$e^{-j \cdot t} = \cos(t) - j \cdot \sin(t)$

Adunând aceste 2 ecuaţii şi împărţind la 2 obţinem:

$\cos(t) = \frac{e^{j \cdot t} + e^{-j \cdot t}}{2}$

Încercaţi să arătaţi asta în Matlab, făcând următoarele:

  • Folosiţi secvenţa de input
     t = [0, pi/6, pi/4, pi/3, pi/2]; 
  • Afişaţi exponenţiala complexă $s_1 = e^{j\cdot t}$, e.g.
     plot(exp(1i*t), 'ro'); 
  • Afişaţi exponenţiala complexă $s_2 = e^{-j \cdot t}$ cu o altă culoare
  • Calculaţi media celor 2 exponenţiale $s_s = \frac{s_1 + s_2}{2}$, i.e. cos(t)
  • Afisaţi secvenţa rezultată în imaginar folosid real(ss) ca valori x şi imag(ss) ca valori y
  • Verificaţi dacă s1, s2 şi ss arată cum v-aţi fi aşteptat!

Acesta este un posibil cod:

complex_exp.m
t = 0:0.1:2*pi;
figure;
plot(exp(1i*t), 'k.');
hold on;
plot(0, 0, 'kx');
t = [0, pi/6, pi/4, pi/3, pi/2];
plot(exp(1i*t), 'ro');
plot(exp(-1i*t), 'bo');
ss = (exp(1i*t)+exp(-1i*t))/2;
plot(real(ss), imag(ss), 'go');
legend('circle', 'origin', 'e^jt', 'e^-jt', '(e^jt + e-jt)/2');

Exerciţiul 4 [1.5p]

La curs am discutat despre sisteme paralele. Acum vom folosi un exemplu simplu de sistem paralel folosit pentru a crea efectul de ecou. Ideea de bază e ca un sistem să replice semnalul de intrare în timp ce un altul îl întârzie. La final cele două sunt adunate.

Task-ul vostru pentru a replica experimentul:

  • Având semnalul de intrare cu o voce in fişierul this.
  • Faceţi o copie a semnalului şi întârziaţi-o (de ex cu 0.1 secunde. Trebuie stiut ca semnalul este esantionat cu o frecvență de 8000 Hz).
  • Adunaţi cele 2 semnale.
  • Ascultaţi semnalul original şi pe cel rezultat pentru a auzi diferenţa. Pentru a asculta semnalele folosiţi funcţia 'sound'.

Atentie: modificare de ultim moment: 0.1 secunde, adica 800 in loc de 500 esantioane

Acesta este un exemplu de rezolvare:

ecou.m
load('voice.mat');
sound(y);
pause(3);
plot(y);
l = length(y);
d = 0.1 * 8000;
y2 = zeros(length(y), 1);
y2(d+1:end,1) = y(1:l-d);
y3 = y + y2;
sound(y3, 8000);
figure;
plot(1:l, [y';y2';y3']);

Exerciţiul 5 [3p]

Avem un sistem de feedback precum cel din imaginea următoare:

Să presupunem că folosim acest sistem pentru sistemul de pilot automat al maşinii, unde x(t) este o constantă ce reprezintă viteza dorită, iar y(t) este viteza maşinii măsurată de vitezometru. În această aplicaţie, sistemul 2 este sistemul identitate (intrare = ieşire).

Să construim acest sistem având în vedere următoarele constrângeri:

  • viteza initială a maşinii este 7
  • valoarea iniţială a secvenţei de feedback (output-ul lui S2), f, este 0
  • valoarea iniţială pentru secvenţa de diferenţă, e, este 0
  • valoarea de input a sistemului de pilot automat, x, este o secvenţă de tipul [60, 60, …, 60]
  • primul sistem, S1, primeste 2 input-uri: viteza curentă şi diferenţa e(i). Bazându-se pe acestea, actualizează viteza curentă după cum urmează:
    • Dacă e(i) > 10, atunci y(i+1) = y(i) + 10
    • altfel dacă e(i) > 0, atunci y(i+1) = y(i) + 1
    • altfel dacă e(i) == 0, atunci y(i+1) = y(i)

Construiţi sistemul S1 ca o funcţie Matlab cu 2 parametrii (viteza_curentă, e), care afişează următoarea viteză curentă ca mai sus. În Matlab puteţi folosi o instrucţiune for pentru asta:

N = 20;
y = zeros(1,N);
y(1) = 7;
for i=1:N-1
  ...
  y(i+1) = S1(y(i), e(i));
end

Rulaţi sistemul de N = 20 ori şi afişaţi outputul sistemului.

Un exemplu de soluţie:

sys1.m
function y=sys1(speed, e)
%SYS1 Simulates a signal system
%   [y] = SYS1(speed, e)
%   returns the current state (speed) after applying the input e
 
if abs(e) > 10
    k = 5;
else
    k = 1;
end
if e > 0
    y = speed + k;
elseif e < 0
    y = speed - k;
else
    y = speed;
end    
cruise_control.m
% Simulate a cruise control system
N = 20;
y = zeros(1, N);
f = zeros(1, N);
e = zeros(1, N);
x = 60*ones(1,N);
 
y(1) = 7; % Initial speed
for i=1:N-1
    e(i) = x(i)-f(i);
    y(i+1) = sys1(y(i), e(i));
    f(i+1) = y(i+1);
end
 
figure;
plot(1:N, e, 'r');
hold on;
plot(1:N, y, 'g');
legend('e', 'y');

ps/laboratoare/02.txt · Last modified: 2018/10/22 16:33 by ionut.gorgos
CC Attribution-Share Alike 3.0 Unported
www.chimeric.de Valid CSS Driven by DokuWiki do yourself a favour and use a real browser - get firefox!! Recent changes RSS feed Valid XHTML 1.0