Plotting correlation coefficient values against time? - matlab

my correlation coefficient values are:
corr=[0.54 0.81 0.21 0.61 0.52 0.47 -0.42 -0.20].
The corresponding time for these correlation coefficient values are:
T=[00:00 - 00:27:02 00:27:02 - 00:35:02 00:35:02 - 00:47:02 00:47 - 00:59:55 01:05:02 - 01:12 01:15 - 01:25 01:27 - 01:35 01:35 - 01:45 ].
The time is given in hour: minute: second format.I want to plot the correlation coefficient values against time. Also, I want to get a 95% confidence line. The example is given in the link https://www.researchgate.net/post/plotting_correlation_coefficient_values_against_time. any help will be appreciated. thanks

first I'm splitting the date strings into start & end times and then I'm converting them to numbers:
coeffs = [0.54 0.81 0.21 0.61 0.52 0.47 -0.42 -0.20];
T = {'00:00 - 00:27:02', '00:27:02 - 00:35:02', '00:35:02 - 00:47:02', '00:47 - 00:59:55', '01:05:02 - 01:12', '01:15 - 01:25', '01:27 - 01:35', '01:35 - 01:45'};
% split to start and end times
startEndTimes = cellfun(#(str) strsplit(str,' - '),T,'UniformOutput',0);
startTimes = cellfun(#(c) c{1},startEndTimes,'UniformOutput',0);
endTimes = cellfun(#(c) c{2},startEndTimes,'UniformOutput',0);
% add seconds where missing
missingSecondsIdx = cellfun(#length,startTimes) == 5;
startTimes(missingSecondsIdx) = cellfun(#(str) [str ':00'],startTimes(missingSecondsIdx),'UniformOutput',0);
missingSecondsIdx = cellfun(#length,endTimes) == 5;
endTimes(missingSecondsIdx) = cellfun(#(str) [str ':00'],endTimes(missingSecondsIdx),'UniformOutput',0);
% convert time strings to numbers
startTimeNums = datenum(startTimes,'HH:MM:SS');
EPS = 1e-4;
endTimeNums = datenum(endTimes,'HH:MM:SS') - EPS;
% interpolate coefficients on "continous" time vector
contTime = linspace(startTimeNums(1),endTimeNums(end),200);
repCoeffs = repmat(coeffs,[2 1]);
repCoeffs = repCoeffs(:);
allTimes = [startTimeNums';endTimeNums'];
allTimes = allTimes(:);
contCoeffs = interp1(allTimes,repCoeffs,contTime);
% plot
plot(contTime,contCoeffs,'b')
hold on;
plot(startTimeNums,coeffs,'og')
plot(endTimeNums,coeffs,'*r')
datetick('x','HH:MM')
xlabel('TIME [HH:MM]')
ylabel('CORRELATION COEFFICIENTS')

Related

How to plot discrete time signal by MATLAB

Given the message signal s(t) = 2cos(40*pi*t) - sin(12*pi*t), how to plot s(t) within 2 second, after 2 second, s(t) = 0 with frequency = 200Hz and sampling number = 500 points?
Sampling a Signal at a Specific Frequency and for a Set Number of Samples
This question has several parts. The first task would be to create a vector t that has separated by the Sampling_Period. Here the Sampling_Frequency is equal to 200Hz, therefore the Sampling_Period = 1/Sampling_Frequency; which equals 0.005 seconds. This vector should run from 0.005 seconds (sample 1) to 2.5 seconds (sample 500). The second task would be to create a step function denoted as u. Here I use an anonymous function that is equal to 0 after time, t is greater than 2 seconds. By multiplying this step function with the sinusoid a truncated version of the function that is 0 after 2 seconds is created.
Sampling Conventions:
Sampling Frequency = 200Hz
Sampling Period = 1/200Hz = 0.005s
Start Time = 0.005s
End Time = (Number of Samples) × (Sampling Period) = (500 samples) × (0.005s) = 2.5s
%Sampling properties%
Sampling_Frequency = 200;
Sampling_Period = 1/Sampling_Frequency;
Number_Of_Samples = 500;
%Creating the time vector%
Start_Time = 0;
End_Time = Number_Of_Samples*Sampling_Period;
t = (Sampling_Period: Sampling_Period: End_Time);
%Step function that ends at 2s%
u = #(t) (t <= 2);
s = #(t) (2*cos(40*pi*t) - sin(12*pi*t)).*u(t);
stem(t,s(t),'Marker','.');
title("Sinusoid Sampled at " + num2str(Sampling_Frequency) + " Hz and the First " + num2str(Number_Of_Samples) + " Samples");
xlabel("Time (s)"); ylabel("Amplitude");
Ran using MATLAB R2019b

How to find 3 hourly averages?

In the below code, each y is of 8 min duration. Once I generate the Powerr matrix I have what I Need but How do i do 3 hour averages? Should i do within the for loop or once I generate the Powerr matrix can i still be able to find out the 3 hourly averages of my data? thanks in advance.
tic
profile on
warning('off','MATLAB:audiovideo:wavread:functionToBeRemoved');
neglect_the_first_few= 5;
lastfile = 10;
Powerr = zeros(2049,10);
count =[];
parfor count = neglect_the_first_few + 1 :lastfile
% time_spectrum(timeindex) = timecount;
warning('off','MATLAB:audiovideo:wavread:functionToBeRemoved');
% infiles = find(timestamp >= timecount & timestamp <= (timecount + timestep));
% if ~isempty(infiles)
% if isnan(time_spectrum)
% time_spectrum(timeindex) = NaN
% end
y= [];
% for inputfile = infiles'
fn = [directory '/001/' file_names(count,:)];
[y,fs,nbits] = wavread(fn,'native');
disp(['sampling freq is ',num2str(fs),' hz. length of y is ',num2str(size(y)),'filenumber is ',num2str(count)])
% end
y = y- mean(y);
Y = double(y).*(1.49365435131571e-07);%CONVERSION - volts per bit for 24bit channel
% clear y;
nooverlap =[];%number of overlapped segments set to zero on Nov20th 2017
[Poww,fr] = pwelch(Y,hanning_window,nooverlap,nfft,fs);%no overlap taken into account%
Powerr(:,count) = Poww;
end
fr is independent from the parfor iteration count. So,this variable did not get transferred to the host from workers. Write fr(count)=...
You've done it correctly for Powerr.

Speed up calculation of maximum of normxcorr2

I need to calculate the maximum of normalized cross correlation of million of particles. The size of the two parameters of normxcorr2 is 56*56. I can't parallelize the calculations. Is there any suggestion to speed up the code especially that I don't need all the results but only the maximum value of each cross correlation (to know the displacement)?
Example of the algorithm
%The choice of 170 particles is because in each time
%the code detects 170 particles, so over 10000 images it's 1 700 000 particles
particle_1=rand(54,54,170);
particle_2=rand(56,56,170);
for i=1:170
C=normxcorr2(particle_1(:,:,i),particle_2(:,:,i));
L(i)=max(C(:));
end
I don't have MATLAB so I ran the following code on this site: https://www.tutorialspoint.com/execute_matlab_online.php which is actually octave. So I implemented "naive" normalized cross correlation and indeed for these small images sizes the naive performs better:
Elapsed time is 2.62645 seconds - for normxcorr2
Elapsed time is 0.199034 seconds - for my naive_normxcorr2
The code is based on the article http://scribblethink.org/Work/nvisionInterface/nip.pdf which describes how to calculate the standard deviation needed for the normalization in an efficient way using integral image, this is the box_corr function.
Also, MATLAB's normxcorr2 returns a padded image so I took the max on the unpadded part.
pkg load image
function [N] = naive_corr(pat,img)
[n,m] = size(img);
[np,mp] = size(pat);
N = zeros(n-np+1,m-mp+1);
for i = 1:n-np+1
for j = 1:m-mp+1
N(i,j) = sum(dot(pat,img(i:i+np-1,j:j+mp-1)));
end
end
end
%w_arr the array of coefficients for the boxes
%box_arr of size [k,4] where k is the number boxes, each box represented by
%4 something ...
function [C] = box_corr2(img,box_arr,w_arr,n_p,m_p)
% construct integral image + zeros pad (for boundary problems)
I = cumsum(cumsum(img,2),1);
I = [zeros(1,size(I,2)+2); [zeros(size(I,1),1) I zeros(size(I,1),1)]; zeros(1,size(I,2)+2)];
% initialize result matrix
[n,m] = size(img);
C = zeros(n-n_p+1,m-m_p+1);
%C = zeros(n,m);
jump_x = 1;
jump_y = 1;
x_start = ceil(n_p/2);
x_end = n-x_start+mod(n_p,2);
x_span = x_start:jump_x:x_end;
y_start = ceil(m_p/2);
y_end = m-y_start+mod(m_p,2);
y_span = y_start:jump_y:y_end;
arr_a = box_arr(:,1) - x_start;
arr_b = box_arr(:,2) - x_start+1;
arr_c = box_arr(:,3) - y_start;
arr_d = box_arr(:,4) - y_start+1;
% cumulate box responses
k = size(box_arr,1); % == numel(w_arr)
for i = 1:k
a = arr_a(i);
b = arr_b(i);
c = arr_c(i);
d = arr_d(i);
C = C ...
+ w_arr(i) * ( I(x_span+b,y_span+d) ...
- I(x_span+b,y_span+c) ...
- I(x_span+a,y_span+d) ...
+ I(x_span+a,y_span+c) );
end
end
function [NCC] = naive_normxcorr2(temp,img)
[n_p,m_p]=size(temp);
M = n_p*m_p;
% compute template mean & std
temp_mean = mean(temp(:));
temp = temp - temp_mean;
temp_std = sqrt(sum(temp(:).^2)/M);
% compute windows' mean & std
wins_mean = box_corr2(img,[1,n_p,1,m_p],1/M, n_p,m_p);
wins_mean2 = box_corr2(img.^2,[1,n_p,1,m_p],1/M,n_p,m_p);
wins_std = real(sqrt(wins_mean2 - wins_mean.^2));
NCC_naive = naive_corr(temp,img);
NCC = NCC_naive ./ (M .* temp_std .* wins_std);
end
n = 170;
particle_1=rand(54,54,n);
particle_2=rand(56,56,n);
[n_p1,m_p1,c_p1]=size(particle_1);
[n_p2,m_p2,c_p2]=size(particle_2);
L1 = zeros(n,1);
L2 = zeros (n,1);
tic
for i=1:n
C1=normxcorr2(particle_1(:,:,i),particle_2(:,:,i));
C1_unpadded = C1(n_p1:n_p2 , m_p1:m_p2);
L1(i)=max(C1_unpadded(:));
end
toc
tic
for i=1:n
C2=naive_normxcorr2(particle_1(:,:,i),particle_2(:,:,i));
L2(i)=max(C2(:));
end
toc

plotting volume-time graph of .wav file

I'm trying to get volume-time graph of .wav file. First, I recorded sound (patient exhalations) via android as .wav file, but when I read this .wav file in MATLAB it has negative values. What is the meaning of negative values? Second, MATLAB experts could you please check if the code below does the same as written in my comments? Also another question. Y = fft(WindowArray);
p = abs(Y).^2;
I took the power of values returned from fft...is that correct and what is the goal of this step??
[data, fs] = wavread('newF2');
% read exhalation audio wav file (1 channel, mono)
% frequency is 44100 HZ
% windows of 0.1 s and overlap of 0.05 seconds
WINDOW_SIZE = fs*0.1; %4410 = fs*0.1
array_size = length(data); % array size of data
numOfPeaks = (array_size/(WINDOW_SIZE/2)) - 1;
step = floor(WINDOW_SIZE/2); %step size used in loop
transformed = data;
start =1;
k = 1;
t = 1;
g = 1;
o = 1;
% performing fft on each window and finding the peak of windows
while(((start+WINDOW_SIZE)-1)<=array_size)
j=1;
i =start;
while(j<=WINDOW_SIZE)
WindowArray(j) = transformed(i);
j = j+1;
i = i +1;
end
Y = fft(WindowArray);
p = abs(Y).^2; %power
[a, b] = max(abs(Y)); % find max a and its indices b
[m, i] = max(p); %the maximum of the power m and its indices i
maximum(g) = m;
index(t) = i;
power(o) = a;
indexP(g) = b;
start = start + step;
k = k+1;
t = t+1;
g = g+1;
o=o+1;
end
% low pass filter
% filtering noise: ignor frequencies that are less than 5% of maximum frequency
for u=1:length(maximum)
M = max(maximum); %highest value in the array
Accept = 0.05* M;
if(maximum(u) > Accept)
maximum = maximum(u:length(maximum));
break;
end
end
% preparing the time of the graph,
% Location of the Peak flow rates are estimated
TotalTime = (numOfPeaks * 0.1);
time1 = [0:0.1:TotalTime];
if(length(maximum) > ceil(numOfPeaks));
maximum = maximum(1:ceil(numOfPeaks));
end
time = time1(1:length(maximum));
% plotting frequency-time graph
figure(1);
plot(time, maximum);
ylabel('Frequency');
xlabel('Time (in seconds)');
% plotting volume-time graph
figure(2);
plot(time, cumsum(maximum)); % integration over time to get volume
ylabel('Volume');
xlabel('Time (in seconds)');
(I only answer the part of the question which I understood)
Per default Matlab normalizes the audio wave to - 1...1 range. Use the native option if you want the integer data.
First, in your code it should be p = abs(Y)**2, this is the proper way to square the values returned from the FFT. The reason why you take the absolute value of the FFT return values is because those number are complex numbers with a Real and Imaginary part, therefore the absolute value (or modulus) of an imaginary number is the magnitude of that number. The goal of taking the power could be for potentially obtaining an RMS value (root mean squared) of your overall amplitude values, but you could also have something else in mind. When you say volume-time I assume you want decibels, so try something like this:
def plot_signal(file_name):
sampFreq, snd = wavfile.read(file_name)
snd = snd / (2.**15) #Convert sound array to floating point values
#Floating point values range from -1 to 1
s1 = snd[:,0] #left channel
s2 = snd[:,1] #right channel
timeArray = arange(0, len(snd), 1)
timeArray = timeArray / sampFreq
timeArray = timeArray * 1000 #scale to milliseconds
timeArray2 = arange(0, len(snd), 1)
timeArray2 = timeArray2 / sampFreq
timeArray2 = timeArray2 * 1000 #scale to milliseconds
n = len(s1)
p = fft(s1) # take the fourier transform
m = len(s2)
p2 = fft(s2)
nUniquePts = ceil((n+1)/2.0)
p = p[0:nUniquePts]
p = abs(p)
mUniquePts = ceil((m+1)/2.0)
p2 = p2[0:mUniquePts]
p2 = abs(p2)
'''
Left Channel
'''
p = p / float(n) # scale by the number of points so that
# the magnitude does not depend on the length
# of the signal or on its sampling frequency
p = p**2 # square it to get the power
# multiply by two (see technical document for details)
# odd nfft excludes Nyquist point
if n % 2 > 0: # we've got odd number of points fft
p[1:len(p)] = p[1:len(p)] * 2
else:
p[1:len(p) -1] = p[1:len(p) - 1] * 2 # we've got even number of points fft
plt.plot(timeArray, 10*log10(p), color='k')
plt.xlabel('Time (ms)')
plt.ylabel('LeftChannel_Power (dB)')
plt.show()
'''
Right Channel
'''
p2 = p2 / float(m) # scale by the number of points so that
# the magnitude does not depend on the length
# of the signal or on its sampling frequency
p2 = p2**2 # square it to get the power
# multiply by two (see technical document for details)
# odd nfft excludes Nyquist point
if m % 2 > 0: # we've got odd number of points fft
p2[1:len(p2)] = p2[1:len(p2)] * 2
else:
p2[1:len(p2) -1] = p2[1:len(p2) - 1] * 2 # we've got even number of points fft
plt.plot(timeArray2, 10*log10(p2), color='k')
plt.xlabel('Time (ms)')
plt.ylabel('RightChannel_Power (dB)')
plt.show()
I hope this helps.

Using structure matlab code

I have recently been working in Matlab, so there are questions. Look at the code, please. If amountOfOptions = 2, I should get OptionPrice = [x x] . Vector Size OptionPrice(1x2). It seems he receives the output it produces but it gives the last result of the assignment.
function [startStockPrice, strike, barrier, riskFreeRate, timeToExpiry, volatility, CallOrPut, UpOrDown, OptionPrice, time] = OutBarrierOption(amountOfOptions)
%%%%%%%%%% Option parameters %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
startStockPrice = 70 + 40 * rand(1,amountOfOptions); % Stock price starts at $100.
strike = 120 + 30 * rand(1,amountOfOptions); % Strike price for the option ($).
barrier = 300 + 300 * rand(1,amountOfOptions); % Barrier price for the option ($).
riskFreeRate = 0.05 + 0.1 * rand(1,amountOfOptions); % 0.5 annual percent.
timeToExpiry = fix(1 + 3 * rand(1, amountOfOptions)); % Lifetime of the option in years. (Time to maturity)
volatility = 0.35 + 0.3 * rand(1,amountOfOptions); % 20% annual volatility. % UpOrDown - 'U' or 'D'
M = 1e4; % Number of Monte-Carlo trials
N = 100; % Number of observations
OptionPrice = 0;
tic;
for k = 1:amountOfOptions
dt(k)=timeToExpiry(k)/N;
for i=1:M
S(1) = startStockPrice(k)*exp((riskFreeRate(k)-(volatility(k)*volatility(k)/2)*dt(k)) + volatility(k)*sqrt(dt(k))*randn);
final_vals=[S(1)];
for j=1:N-1;
S(j + 1) = S(j)* exp((riskFreeRate(k) - 0.5* volatility(k)*volatility(k))*dt(k) + volatility(k)* sqrt(dt(k))* randn);
final_vals=S(1:j+1);
end
end
if max(final_vals) <= barrier(k)
option_values=max(final_vals - strike(k),0); % Evaluate the Call option options
present_vals = exp(-riskFreeRate(k)*timeToExpiry(k))*option_values; % Discount under r-n assumption
OptionPrice = mean(present_vals); % Take the average
else
% Hit the barrier, so the option is withdrawn.
present_vals = 0;
OptionPrice = mean(present_vals);
end
end
time = toc;
end