HiFiForum.nu
Home | Forums | Profile | Register | Active Topics | Links | Members | Articles | PM | Search | FAQ
Username:
Password:
Save Password
Forgot your Password?

Private Messages
You must log in to check messages
 All Forums
 HiFiForum.nu - Mångfaldens forum
 Teknik och DIY
 Matlab-fråga till Wolfie eller rikkit..nånting
 New Topic  Topic Locked
 Printer Friendly
Author Previous Topic Topic Next Topic  

marens
Member

3368 Posts

Posted - 2003/05/13 :  17:09:43  Show Profile Send marens a Private Message
Går det att använda matlab (eller scilab) på något smidigt sätt för att importea ljudfiler och allpass filtrera dem?

Edited by - marens on 2003/05/13 22:21:01

Nagref
Member

113 Posts

Posted - 2003/05/13 :  22:08:33  Show Profile Send Nagref a Private Message
Det borde gå bra! Hur det exakt ska göras vet jag dock inte men kanske Wolfie vet?

Wolfie? Eller Rikkititav?

Assisterar Holographic Audio och Larsen Hifi
VD för Acoustic Landscape
R&D-ansvarig för Acoustic Illusion
Go to Top of Page

DasKapital
Member

614 Posts

Posted - 2003/05/13 :  22:36:29  Show Profile Send DasKapital a Private Message
Det finns import-kommandon för wav-filer. När du väl importerat filen är det bara att köra den genom ditt system. Finns käcka kommanond för att sätta upp dynamiska system. tf(num,den) sätter upp en överföringsfunktion. lsim(tf(),insignal,t) kör insignalen genom systemet.

Ett lab-pm till en labb jag genomlidit med har lite grundläggandew om systemsimulering i matlab: http://www.s2.chalmers.se/undergraduate/courses/ess050/labpm.pdf
Hur wav-importen funkar kommer jag tyvärr inte ihåg mer än att jag har lyckats att imortera en wav-fil en gång.

Ino Audio for life
Go to Top of Page

rikkitikkitavi
Member

653 Posts

Posted - 2003/05/13 :  22:48:48  Show Profile Send rikkitikkitavi a Private Message
rikkitik-whatever :) är tyvärr inte längre kommen än att han försöker lära sig programmera mer än enkla diffekvationer i matlab men kan ge följande svar:

kommandot wavread löser detta problem

y = wavread(file) läser in wavfilen file i vektorn y.


man kan också direkt i rullgardinmenyerba File-Import importera en wav-fil

sök gärna i hjälpen, wavread kan göra mer än så, även kommandot wavwrite. Fullständig dokumentation finns för nerladdning från www.mathworks.com (ca 400 Mb) , plus massor av sample programs.

angående filtrering, så långt har jag inte kommit.

/rickard


I m only in it for the DIY
Go to Top of Page

marens
Member

3368 Posts

Posted - 2003/05/13 :  23:17:59  Show Profile Send marens a Private Message
Har suttit ett bra tag nu med scilab och har faktiskt lyckats importera en wav-fil.:)

Får sätta mig in mera i scilab hjälpen vilka kommandon jag måste använda för att filtrera signalen men det ska gå. Kan posta hur man gör sen om jag kommer nån vart och någon är intresserad.

Syftet är helt enkelt att bränna en skiva med och utan fasdistorsion och testa hur hörbart det är.
Go to Top of Page

dax
Member

644 Posts

Posted - 2003/05/14 :  23:50:49  Show Profile Send dax a Private Message
MATLAB har en mängd läckra kommandon. bl.a wavread (tar en wavfil och skapar rådata), wavwrite (sapar en wavfil från rådata), wavrecord... Har du en toolbox (filterdesign) så finns det även mycket olika filterfunktioner.

Do not stagedive at home alone!
Go to Top of Page

Wolfie
Member

752 Posts

Posted - 2003/05/15 :  07:59:00  Show Profile  Visit Wolfie's Homepage Send Wolfie a Private Message
Hallo :)

Ser att du knappast behöver min hjälp i denna fråga :)

Angående filtrering så är det helt klart enklast att ha filterdesign toolbox.
Men det finns ett kommando som heter filt() eller filter() (help filt, help filter ger dig vad du behöver).

Angående att bygga filter så är det ganska enkelt. Du behöver ju eg. bara specifiera filtret i frekvensdomän. E.g. sätta upp överföringsfunktionen.

ex: (nånting sådant här, kommer inte ihåg alla kommandona direkt i huvedet men vi gör ett försök).

[Y,fs] = wavread('c:\fulalatar\bordellmammasvisor\runkamigmedvitahandskar.wav'); // ;)

syms(s); //eller dyl kommandonamn för att göra om s (om det nu behövs) till en symbol

H= (1+s)/(s^2+3s-1);

H = tf(H); //H ska nu vara en överföringsfunktion... (kör help tf för korrekt syntax)

sen var det något kommando för att få fram filterkoefficienterna... Bah... som jag inte kan komma ihåg.
Men det står säkert väl dokumenterat i hjälpen... (har inte Matlab här)

sen så är det e.g. bara att köra Y2=filter(B,A,Y,fs); //ännu en gång kolla med help filter för rätt syntax
//(samplingsfrekvenser o dylikt) i detta exempel är B,A lika med filterkoefficienterna.

Vill man ha ett ordinarie butterworth, eller chebychev filter så
skriver man helt enkelt [B,A] = butter(nånting, nånting med normaliserad gränsfrekvens, nånting med samplingsfrekvens); //Help butter :) För ett butterworth filter alltså.

cheby1(), cheby2() eller liknande för ett Chebychev 1 eller 2...

Finns naturligvis snabbkommandon för andra typer av filter oxo.

Dock finns ju det där görsmidiga programmet som heter... nånting där man grafiskt specar stoppband, passband, rippel i stoppband och passband etc. etc. och som sedan spottar ut filterkoefficienterna rätt upp och ner i 2 st vektorer, hur bra som helst. Kan dock inte minnas namnet på programmet, samt att det troligtvis ligger med i filterdesign toolbox.

Jeeeej tack KAU för att ni aldrig stänger mitt studentkonto på servrarna ;) Kom just åt lite labmaterial och plopp så kom namnet upp ju :) SPtool heter programmet som du kan göra diverse signalbehandling i.

bara att skriva i kommandofönstret

>>sptool





Ingen ordning utan kaos!
Go to Top of Page

Wolfie
Member

752 Posts

Posted - 2003/05/15 :  08:00:34  Show Profile  Visit Wolfie's Homepage Send Wolfie a Private Message
Här har jag stulit en lab... Hmm... SLäng in koden i kompilatorn och se vad den gör... :)
Har något med filtrering att göra iaf. Du kanske kan få någe hjälp därifrån.

NM = 1024;
NN = NM-1;
n = 0:NN;
Fs = 200; % Number of sample points per period
x = square(2*pi*1/Fs*n);

%[b,a] = butter(3, 0.34); % 1 = Nyquist freq corresponding to half the sample rate
[b,a] = cheby1(3, 3, 0.34); % 1 = Nyquist freq corresponding to half the sample rate
% (0.2 = f0/(fs/2) )
h = impz(b,a,n); % Impulse response according to the vector n
y = conv(h,x); % Convolution (Faltning)
y = y(1:NM); % Skip the tail to get the same length of the vectors

[hjw,w] = freqz(b,a, NM,'whole'); % along the whole unit circle in the z-plane
Fx = fft(x);
Fy = fft(y);
Fys = (Fx .* hjw.'); % .' non-conjugate transpose!
ysmth = real(ifft(Fys)); % force real

plot(n,x, n,h); title( 'Input signal and impulse response.')
pause
semilogy(w,abs(Fx), w,abs(Fy), w,abs(Fys)); title( 'Comparison in the frequency domain.')
pause
zplane(b,a); title( 'z-plane pole - zero plot.')
pause
freqz(b,a, NM,'whole'); % plots the frequency response magnitude and phase
pause
plot(n,y, n,ysmth, n,x); title( 'Comparison in the time domain.')


% ALTERNATIVELY:
% f = 1e3; % frequency
% fs =200e3; % sample frequency
% x = square(2*pi*f/fs*n);
% imp = [1, zeros(1,1023)];
% [b,a] = cheby1(5, .5, 20e3 /(fs/2)); % [b,a] = cheby1(5, .5, 0.2);
% h = filter(b,a,imp); % Impulse response
% [hjw,w] = freqz(b,a, NM/2, fs); % only the upper half of the unit circle in the z-plane

%semilogy(w,abs(hjw))
%pause
%p = unwrap(angle(hjw));
%plot(w,p*180/pi); grid
%pause
%semilogy(w,abs(Fx))
%pause
%semilogy(w,abs(Fy))
%pause
%semilogy(w,abs(Fys))

Ingen ordning utan kaos!
Go to Top of Page

Isidor
Member

166 Posts

Posted - 2003/05/15 :  13:13:46  Show Profile Send Isidor a Private Message
Här följer ett litet skript jag slängde ihop för allpassfiltrering av wavefil (i exemplet 3:e ordningens Butterworth och 500 Hz). Det kräver att man har Signal Processing Toolbox installerat för tillgång till kommandot "butter". Annars kan man alltid, som Wolfie är inne på ovan, definiera filtret i frekvensplanet, ta fram impulssvaret via invers fft och sedan falta detta med waven.


clear
warning off

%Import
[y,fs] = wavread('xxx.wav');

%Filterdefinition
fc = 500;
order = 3;
Wn = [fc/fs];
[b,a] = butter(order,Wn);
[d,c] = butter(order,Wn,'high');

%Filtrering lågpass och högpass
ylp = filter(b,a,y);
yhp = filter(d,c,y);

%Summering till allpass
yap = ylp+yhp;

%Allpassfiltrerad wav-fil
scalefact = max(max(abs(yap)));
wavwrite(yap/scalefact,fs,16,'xxxallpass.wav');

Edited by - Isidor on 2003/05/15 13:52:46
Go to Top of Page

marens
Member

3368 Posts

Posted - 2003/05/16 :  15:45:31  Show Profile Send marens a Private Message
Ni ska ha supertack för detta!

Ska sätta mig in i det så fort jag får tid.

Edited by - marens on 2003/05/16 15:47:26
Go to Top of Page

dax
Member

644 Posts

Posted - 2003/05/16 :  16:39:30  Show Profile Send dax a Private Message
Och inte nog med detta! Vill du testa att jusera frekvensgången utan fasresponsen förändras kan du testa funktione FIR2. Man får en targetfilterkurva som kan sättas godtyckligt medan faskurvan håller sig kring 0. Mycket användbar!

Do not stagedive at home alone!
Go to Top of Page

Claes_Ireland
Member

2146 Posts

Posted - 2003/05/16 :  22:04:43  Show Profile Send Claes_Ireland a Private Message
Det här blev ju intressant kanske.
Om man mäter upu frekvensgången i sitt lyssningsrum,
kan man kanske ta en låt, kompensera låten till lyssningsrummet,
så har man en ide om hur det skulle låta med en Behringer eller liknande. Någon som orkar testa? Med en brännare i datorn så är det nog ganska görbart. Har inte använt matlab sen läääänge så har själv ingen hjälp att ge.

Sweden->Ireland->Australia->Ireland->...Sweden...Glad to be back
Go to Top of Page

dax
Member

644 Posts

Posted - 2003/05/16 :  23:45:00  Show Profile Send dax a Private Message
Ja, det kan man!

Do not stagedive at home alone!
Go to Top of Page

Wolfie
Member

752 Posts

Posted - 2003/05/17 :  09:50:23  Show Profile  Visit Wolfie's Homepage Send Wolfie a Private Message
Javisst! Det är ju faktiskt inga problem att kompensera för rummet med en låt mha exempelvis fir2() eller om man pular med SPtool.

Najs dax! Kom faktiskt själv inte ihåg fir2 :) (var rätt längesen jag lekte ordentligt med Matlab).

Däremot så har jag byggt ett program i Matlab där man i en grafisk miljö kan sitta och pula med just .wav-filer. Dock kräver det att filteralgoritmer, kvantiseringsalgoritmer eller vad man nu vill göra skrivs i matlabkod (.m filer). Sen så får man se originalsignalen i ett fönster och resultatet i ett annat. Har även byggt in möjligheter för att se spectogram (tid i x-axel och frekvens i y-axel, intensitet på frekvensinnehåll ligger färgkodat.
Dock så är programmet ruggigt segkört.

Ingen ordning utan kaos!
Go to Top of Page

dax
Member

644 Posts

Posted - 2003/05/17 :  11:45:53  Show Profile Send dax a Private Message
Har man möjlighet att mäta upp sin frekvensgång (för att veta vad och var man vill modifiera)kan man skriva funktioner som adaptivt estimerar filterkoefficienterna till dess att man når önskat (godtyckligt) frekvenssvar. Därefter kan man utnyttja dessa koeeficienter till att filtrera musiken med!

Do not stagedive at home alone!
Go to Top of Page

Isidor
Member

166 Posts

Posted - 2003/05/17 :  14:29:15  Show Profile Send Isidor a Private Message
Den mest direkta metoden för högtalar/rumskorrigering kan åstadkommas genom att:

1. Mäta upp frekvenssvaret
2. Inverstransformera frekvenssvaret till impulssvar (som eventuellt trunkeras)
3. Generera korrektionsterm ur impulssvaret
4. Falta waven med korrektionstermen

Detta går att göra i Matlab och kräver inte många rader kod, men faller i praktiken på att det blir extremt låååååångsamt att utföra faltningen. Det finns säkert möjligheter att vara lite smart och snabba upp det hela hyfsat men Matlab lider ju alltid av att vara ett högnivåspråk när det gäller snabbhet. En normal wavefil ligger ju omkring sådär 50 MB så det blir en del beräkningar som skall utföras och detta tar tid i Matlab.

Edited by - Isidor on 2003/05/17 14:37:27
Go to Top of Page

Isidor
Member

166 Posts

Posted - 2003/05/17 :  17:21:01  Show Profile Send Isidor a Private Message
Ett mer elegant, men kanske lite mer svårgreppat, sätt att göra det hela på är i grova drag att:

1. Mäta upp frekvenssvaret Gf(f) (eventuellt medelvärdesbildat över lyssnarytan)
2. Definiera målfrekvenssvaret Gm(f) (bandbreddsbegränsning, personlig smak o.s.v.)
3. Bilda korrektionskvoten k(f) = Gm/Gf
4. Inverstransformera k(f) till korrektionsimpulssvaret k(t)
5. Falta k(t) med waven

Det verkar som om de flesta kommersiella tillämpningarna fungerar på ungefär det här sättet och det är lätt att inse att det ger flera fördelar. Jag har tänkt prova detta i praktiken ett tag nu så det är väl dags att hugga i. Det är ganska enkelt att koda ovanstående i Matlab, men jag gissar att man blir lite trött på beräkningstiderna. Hur som helst är det coooolt med digital korrektion som preprocessning i Matlab och rätt mycket billigare än hårdvaruvarianterna (om man har fri tillgång till Matlab förstås). Tills någon trevlig figur skriver ett DX-filter som gör samma sak fast i realtid så får man väl nöja sig med något som detta.
Go to Top of Page

dax
Member

644 Posts

Posted - 2003/05/17 :  17:44:19  Show Profile Send dax a Private Message
Jag hörde om en kille som filtrerade i realtid med en Linuxburk. Det var nog iofs lite asemblerprogrammering med i bilden!

Man kan ju kasta in filterkoefficienterna i en DSP annars!

Do not stagedive at home alone!
Go to Top of Page

Wolfie
Member

752 Posts

Posted - 2003/05/17 :  17:59:06  Show Profile  Visit Wolfie's Homepage Send Wolfie a Private Message
dax: Några killar i min klass när jag läste på KAU gjorde precis vad du sa. De hade inga problem att få det att fungera faktiskt. Dock så gällde det här olika kamfilter etc. för att få lite roliga ljudeffekter till gitarrer.

Sen så finns det ju faktiskt "plugins" till många olika DSP´s (har lekt lite med Analog Devices...) där du helt enkelt skriver dina filteralgoritmer i Matlab kod och sedan konverteras det till assembler för den specifika DSP´n. Det går tom att tanka ner det rätt i DSP´n via Matlab! (man slipper själv sitta o assemblera.. bla bla bla...)

Sen så går det faktiskt att utföra dessa typer av filteringar i Matlab i realtid oxo. Bäst bör det fungera om man kör någon variant för unix/linux där man ju som SU har bättre tillgång till processortid än i Windows. Det gäller helt enkelt att tweaka Matlab såpass mycket att det går, samt skriva enkla program med få if och for loopar...
Ett tips, som säkert alla vet, för att få for() loopar att gå 1000 ggr snabbare än innan är att alltid fördefiniera variablerna som används i loopen (vilket man ju iof oftast gör) men här ska man även definiera storleken på variablerna! Samt nolla dem innan eller vad man nu vill göra med den innan det ska loopas. Det får sega for loopar att snabbas upp rejält.

Har suttit i ca. 10 veckor med att optimera Matlabkod när jag och en polare gjorde vårt examensjobb... Rätt skoj uppgift ändå att bygga ett ljudlab :) (blidde dock många rader kod... runt 2000 rader för endast kärnan, phu).

Ingen ordning utan kaos!
Go to Top of Page

Isidor
Member

166 Posts

Posted - 2003/05/17 :  21:39:34  Show Profile Send Isidor a Private Message
DSP:er är ju trevliga men lite mer krävande än en timmas Matlab-programmering. Annars är det helt klart en möjlighet för ett framtida projekt. Tyvärr är det mycket annat som har högre prioritet, t.ex. en smal sak som att bygga världens bästa högtalare först. En ganska markant fördel med ren mjukvaruimplementering via t.ex. DirectX är att det blir mycket lättare att få till en multikanalsvariant.

Vill man försöka undvika faltningen i Matlab kan man försöka jobba med FFT som leder till rena multiplikationer istället, men det blir betydligt mer programmeringsarbete i det fallet.

För ren mjukvarufiltrering i realtid finns för övrigt extremt snabba BruteFIR att tillgå, dock bara för UNIX som jag inte tycker är redo för HTPC.
Go to Top of Page
  Previous Topic Topic Next Topic  
 New Topic  Topic Locked
 Printer Friendly
Jump To:
HiFiForum.nu © HiFiForum.nu except: Logos and Trademarks are property of their owners, Comments are property of their posters Go To Top Of Page
Denna sida genererades på 0.69 sekunder. Snitz Forums 2000