How to make a certain pulse function with Matlab? - matlab

How to make a certain pulse function with Matlab, like this function on the graph:
I have the function which generates a pulse, but I want to generate as the graph above
clear all; clc; close all
% Step 1: Calculate Fourier Transform Coefficients
N = 101; % Number of coefficients
D = [];
% Negative Coefficients
for n = -(N-1)/2 : -1
D = [D (1/(n*pi))*sin(n*pi/2)];
end
% Append D0
D0 = 0.5; D = [D D0];
% Positive Coefficients
for n = 1 : (N-1)/2
D = [D (1/(n*pi))*sin(n*pi/2)];
end
% Step 2: Calculate the series terms
series = [];
f0 = 1; % Frequency in Hz
T0 = 1/f0; % Period in seconds
dt = T0/100; % Sample interval
t = -T0 : dt : T0;
for n = -(N-1)/2 : (N-1)/2
r = n + (N+1)/2;
temp = D(r)*exp(j*n*2*pi*f0*t);
series = [series; temp];
end
% Step 3: Summation of the series terms
w = 8*sum(series);
% Step 4: Plot the approximated signal
plot(t,w); grid
xlabel('Time, seconds'); ylabel('signal, s(t)')
title('An approximation of a rectangular singal using Fourier series')'

You need to calculate the continuous Fourier series for your waveform, then modify the coefficients in D to match.
You can find information on general Fourier series elsewhere on the internet.

Related

Calculate the phase of a signal based on the generated data

I have written a simple code to calculate the phase and magnitude of a signal, based on the sinusoidal input given in my problem. I have already determined the magnitude of the signal corresponding to different values of w. More specifically, the phase I want is a vector calculated for different values of w. Notice that the signal I'm talking about is the output signal of a linear process. As matter of fact, I want the phase difference between the input u and the output y, defined for all values of w for all time steps. I have created the time and w vector in my code. Here is the main code I have written in MATAB2021a:
clc;clear;close all;
%{
Problem 2 Simulation, By M.Sajjadi
%}
%% Predifined Parameters
tMin = 0;
tMax = 50;
Ts = 0.01; % Sample Time
n = tMax/Ts; % #Number of iterations
t = linspace(tMin,tMax,n);
% Hint: Frequency Domain
wMin = 10^-pi;
wMax = 10^pi;
Tw = 10;
w = wMin:Tw:wMax; % Vector of Frequency
Nw = length(w);
a1 = 1.8;
a2 = -0.95;
a3 = 0.13;
b1 = 1.3;
b2 = -0.5;
%% Input Generation
M = numel(w);
N = length(t);
U = zeros(M,N);
Y = U; % Response to the sinusoidal Input, Which means the initial conditions are set to ZERO.
U(1,:) = sin(w(1)*t);
U(2,:) = sin(w(2)*t);
U(3,:) = sin(w(3)*t);
Order = 3; % The Order of the Differential Equation, Delay.
%% Main Loop for Amplitude and Phase
Amplitude = zeros(Nw,1); % Amplitude Values
for i=1:numel(w)
U(i,:) = sin(w(i)*t);
for j=Order+1:numel(t)
Y(i,j) = a1*Y(i,j-1) + a2*Y(i,j-2) + a3*Y(i,j-3) + ...
b1*U(i,j-1) + b2*U(i,j-2);
end
Amplitude(i) = max(abs(Y(i,:)));
end
I know I should use fft or findpeaks function in MATLAB, but I do not know how I should do it.

Issue with Discrete Double Fourier Series in MATLAB

The formula for the discrete double Fourier series that I'm attempting to code in MATLAB is:
The coefficient in front of the trigonometric sum (Fourier amplitude) is what I'm trying to extract from the fitting of the data through the double Fourier series seen above. Using my current code, the original function is not reconstructed, therefore my coefficients cannot be correct. I'm not certain if this is of any significance or insight, but the second term for the A coefficients (Akn(1))) is 13 orders of magnitude larger than any other coefficient.
Any suggestions, modifications, or comments about my program would be greatly appreciated.
%data = csvread('digitized_plot_data.csv',1);
%xdata = data(:,1);
%ydata = data(:,2);
%x0 = xdata(1);
lambda = 20; %km
tau = 20; %s
vs = 7.6; %k/s (velocity of CHAMP satellite)
L = 4; %S
% Number of terms to use:
N = 100;
% set up matrices:
M = zeros(length(xdata),1+2*N);
M(:,1) = 1;
for k=1:N
for n=1:N %error using *, inner matrix dimensions must agree...
M(:,2*n) = cos(2*pi/lambda*k*vs*xdata).*cos(2*pi/tau*n*xdata);
M(:,2*n+1) = sin(2*pi/lambda*k*vs*xdata).*sin(2*pi/tau*n*xdata);
end
end
C = M\ydata;
%least squares coefficients:
A0 = C(1);
Akn = C(2:2:end);
Bkn = C(3:2:end);
% reconstruct original function values (verification check):
y = A0;
for k=1:length(Akn)
y = y + Akn(k)*cos(2*pi/lambda*k*vs*xdata).*cos(2*pi/tau*n*xdata) + Bkn(k)*sin(2*pi/lambda*k*vs*xdata).*sin(2*pi/tau*n*xdata);
end
% plotting
hold on
plot(xdata,ydata,'ko')
plot(xdata,yk,'b--')
legend('Data','Least Squares','location','northeast')
xlabel('Centered Time Event [s]'); ylabel('J[\muA/m^2]'); title('Single FAC Event (50 Hz)')

Plotting a collection of sine waves

I have the following code:
Fs = 1000;
T = 1/Fs;
L = 1000;
t = (0:L-1)*T;
k = 25:1:50;
m = 1:1:25;
where k and m are corresponding. I want to plot the 25 sine waves resulting from:
x = m*sin(2*pi*k*t);
I thought about doing it using a for loop that takes one value from m and k each time, but I'm unsure how to proceed.
Below is a very basic plotting solution. You will notice that it's very difficult to see what's going on in the plot, so you might want to consider other ways to present this data.
function q45532082
Fs = 1000;
T = 1/Fs;
L = 1000;
t = (0:L-1)*T;
k = 26:1:50;
m = 1:1:25;
%% Plotting
assert(numel(m) == numel(k)); % We make sure that the number of elements is the same.
figure(); hold on; % "hold" is needed if you want to see all curves at the same time.
for ind1 = 1:numel(m)
plot(t,m(ind1)*sin(2*pi*k(ind1)*t));
end
This is the result:
Note that the number of elements in k and m in your code is different, so I had to change it.
Using the functionality of plot you can also plot all sine waves without a loop:
Fs = 1000;
T = 1/Fs;
L = 1000;
t = (0:L-1)*T;
k = 26:1:50;
m = 1:1:25;
x = m.*sin(2.*pi.*bsxfun(#times,t.',k)); %this results in an L*25 matrix, each column is data of one wave
% or, if you have version 2016b or newer:
% x = m.*sin(2.*pi.*t.'*k);
plot(t,x) % plot all sines at ones
and as #Dev-iL noted, I also had to change k.
The result with L = 1000 is too crowded, so I plot it here with L = 50:

Morlet wavelet transformation function returns nonsensical plot

I have written a matlab function (Version 7.10.0.499 (R2010a)) to evaluate incoming FT signal and calculate the morlet wavelet for the signal. I have a similar program, but I needed to make it more readable and closer to mathematical lingo. The output plot is supposed to be a 2D plot with colour showing the intensity of the frequencies. My plot seems to have all frequencies the same per time. The program does make an fft per row of time for each frequency, so I suppose another way to look at it is that the same line repeats itself per step in my for loop. The issue is I have checked with the original program, which does return the correct plot, and I cannot locate any difference beyond what I named the values and how I organized the code.
function[msg] = mile01_wlt(FT_y, f_mn, f_mx, K, N, F_s)
%{
Fucntion to perform a full wlt of a morlet wavelett.
optimization of the number of frequencies to be included.
FT_y satisfies the FT(x) of 1 envelope and is our ft signal.
f min and max enter into the analysis and are decided from
the f-image for optimal values.
While performing the transformation there are different scalings
on the resulting "intensity".
Plot is made with a 2D array and a colour code for intensity.
version 05.05.2016
%}
%--------------------------------------------------------------%
%{
tableofcontents:
1: determining nr. of analysis f, prints and readies f's to be used.
2: ensuring correct orientation of FT_y
3:defining arrays
4: declaring waveletdiagram and storage of frequencies
5: for-loop over all frequencies:
6: reducing file to manageable size by truncating time.
7: marking plot to highlight ("randproblemer")
8: plotting waveletdiagram
%}
%--------------------------------------------------------------%
%1: determining nr. of analysis f, prints and readies f's to be used.
DF = floor( log(f_mx/f_mn) / log(1+( 1/(8*K) ) ) ) + 1;% f-spectre analysed
nr_f_analysed = DF %output to commandline
f_step = (f_mx/f_mn)^(1/(DF-1)); % multiplicative step for new f_a
f_a = f_mn; %[Hz] frequency of analysis
T = N/F_s; %[s] total time sampled
C = 2.0; % factor to scale Psi
%--------------------------------------------------------------%
%2: ensuring correct orientation of FT_y
siz = size(FT_y);
if (siz(2)>siz(1))
FT_y = transpose(FT_y);
end;
%--------------------------------------------------------------%
%3:defining arrays
t = linspace(0, T*(N-1)/N, N); %[s] timespan
f = linspace(0, F_s*(N-1)/N, N); %[Hz] f-specter
%--------------------------------------------------------------%
%4: declaring waveletdiagram and storage of frequencies
WLd = zeros(DF,N); % matrix of DF rows and N columns for storing our wlt
f_store = zeros(1,DF); % horizontal array for storing DF frequencies
%--------------------------------------------------------------%
%5: for-loop over all frequencies:
for jj = 1:DF
o = (K/f_a)*(K/f_a); %factor sigma
Psi = exp(- 0*(f-f_a).*(f-f_a)); % FT(\psi) for 1 envelope
Psi = Psi - exp(-K*K)*exp(- o*(f.*f)); % correctional element
Psi = C*Psi; %factor. not set in stone
%next step fits 1 row in the WLd (3 alternatives)
%WLd(jj,:) = abs(ifft(Psi.*transpose(FT_y)));
WLd(jj,:) = sqrt(abs(ifft(Psi.*transpose(FT_y))));
%WLd(jj,:) = sqrt(abs(ifft(Psi.*FT_y))); %for different array sizes
%and emphasizes weaker parts.
%prep for next round
f_store (jj) = f_a; % storing used frequencies
f_a = f_a*f_step; % determines the next step
end;
%--------------------------------------------------------------%
%6: reducing file to manageable size by truncating time.
P = floor( (K*F_s) / (24*f_mx) );%24 not set in stone
using_every_P_point = P %printout to cmdline for monitoring
N_P = floor(N/P);
points_in_time = N_P %printout to cmdline for monitoring
% truncating WLd and time
WLd2 = zeros(DF,N_P);
for jj = 1:DF
for ii = 1:N_P
WLd2(jj,ii) = WLd(jj,ii*P);
end
end
t_P = zeros(1,N_P);
for ii = 1:N_P % set outside the initial loop to reduce redundancy
t_P(ii) = t(ii*P);
end
%--------------------------------------------------------------%
%7: marking plot to highlight boundary value problems
maxval = max(WLd2);%setting an intensity
mxv = max(maxval);
% marks in wl matrix
for jj= 1:DF
m = floor( K*F_s / (P*pi*f_store(jj)) ); %finding edges of envelope
WLd2(jj,m) = mxv/2; % lower limit
WLd2(jj,N_P-m) = mxv/2;% upper limit
end
%--------------------------------------------------------------%
%8: plotting waveletdiagram
figure;
imagesc(t_P, log10(f_store), WLd2, 'Ydata', [1 size(WLd2,1)]);
set(gca, 'Ydir', 'normal');
xlabel('Time [s]');
ylabel('log10(frequency [Hz])');
%title('wavelet power spectrum'); % for non-sqrt inensities
title('sqrt(wavelet power spectrum)'); %when calculating using sqrt
colorbar('location', 'southoutside');
msg = 'done.';
There are no error message, so I am uncertain what exactly I am doing wrong.
Hope I followed all the guidelines. Otherwise, I apologize.
edit:
my calling program:
% establishing parameters
N = 2^(16); % | number of points to sample
F_s = 3.2e6; % Hz | samplings frequency
T_t = N/F_s; % s | length in seconds of sample time
f_c = 2.0e5; % Hz | carrying wave frequency
f_m = 8./T_t; % Hz | modulating wave frequency
w_c = 2pif_c; % Hz | angular frequency("omega") of carrying wave
w_m = 2pif_m; % Hz | angular frequency("omega") of modulating wave
% establishing parameter arrays
t = linspace(0, T_t, N);
% function variables
T_h = 2*f_m.*t; % dimless | 1/2 of the period for square signal
% combined carry and modulated wave
% y(t) eq. 1):
y_t = 0.5.*cos(w_c.*t).*(1+cos(w_m.*t));
% y(t) eq. 2):
% y_t = 0.5.*cos(w_c.*t)+0.25*cos((w_c+w_m).*t)+0.25*cos((w_c-w_m).*t);
%square wave
sq_t = cos(w_c.*t).*(1 - mod(floor(t./T_h), 2)); % sq(t)
% the following can be exchanged between sq(t) and y(t)
plot(t, y_t)
% plot(t, sq_t)
xlabel('time [s]');
ylabel('signal amplitude');
title('plot of harmonically modulated signal with carrying wave');
% title('plot of square modulated signal with carrying wave');
figure()
hold on
% Fourier transform and plot of freq-image
FT_y = mile01_fftplot(y_t, N, F_s);
% FT_sq = mile01_fftplot(sq_t, N, F_s);
% Morlet wavelet transform and plot of WLdiagram
%determining K, check t-image
K_h = 57*4; % approximation based on 1/4 of an envelope, harmonious
%determining f min and max, from f-image
f_m = 1.995e5; % minimum frequency. chosen to showcase all relevant f
f_M = 2.005e5; % maximum frequency. chosen to showcase all relevant f
%calling wlt function.
name = 'mile'
msg = mile01_wlt(FT_y, f_m, f_M, K_h, N, F_s)
siz = size(FT_y);
if (siz(2)>siz(1))
FT_y = transpose(FT_y);
end;
name = 'arnt'
msg = arnt_wltransf(FT_y, f_m, f_M, K_h, N, F_s)
The time image has a constant frequency, but the amplitude oscillates resempling a gaussian curve. My code returns a sharply segmented image over time, where each point in time holds only 1 frequency. It should reflect a change in intensity across the spectra over time.
hope that helps and thanks!
I found the error. There is a 0 rather than an o in the first instance of Psi. Thinking I'll maybe rename the value as sig or something. besides this the code works. sorry for the trouble there

Plotting realizations of a stochastic process in the same plot

I want to plot multiple realizations of a stochastic process in matlab. For a single realization I have the following code:
N = 80;
T = dt*N;
dWt = zeros(1,N);
S= repmat(S0,1,N);
S(1) = S0;
dWt = sqrt(dt) * randn;
for t=2:N
dWt(t) = sqrt(dt)*randn;
dSt = k*(mu-S(t-1))*dt + sigma*S(t-1)*dWt(t);
S(t) = S(t-1)+dSt;
end
plot(handles.pMeasure, [0:dt:T],[S0,S]);
I want to replicate this loop n times and plot the results in one plot.
You could add an additional for loop, but it would be best to vectorize everything and calculate all n instances at once:
k = ...
mu = ...
sigma = ...
S0 = ... % Initial condition
dt = ... % Time step
n = ... % Number of instances
N = 80; % Number of time steps, not counting initial condition
T = dt*N; % Final time
rng(1); % Always seed random number generator
dWt = sigma*sqrt(dt)*randn(n,N); % Calculate Wiener increments
S = zeros(n,N+1); % Allocate
S(:,1) = S0; % Set initial conditions
for t = 2:N+1
S(:,t) = S(:,t-1) + k*(mu-S(:,t-1))*dt + S(:,t-1).*dWt(:,t-1);
end
plot(handles.pMeasure,0:dt:T,S)
There are further ways to optimize this if want or you can also try sde_euler in my SDETools Matlab toolbox:
k = ...
mu = ...
sigma = ...
dt = ... % Time step
n = ... % Number of instances
N = 80; % Number of time steps, not counting initial condition
T = dt*N; % Final time
f = #(t,y)k*(mu-y); % Diffusion function
g = #(t,y)sigma*y; % Drift function
t = 0:dt:T; % Time vector
S0 = zeros(n,1); % Initial conditions
opts = sdeset('RandSeed',1,...
'SDEType','Ito'); % Set random seed, specify Ito SDE
S = sde_euler(f,g,t,S0,opts); % Simulate
plot(t,S)