Matlab code of Neural delay differential equation NDDE
5 visualizaciones (últimos 30 días)
Mostrar comentarios más antiguos
Muhammad
el 2 de En. de 2024
Comentada: Muhammad
el 5 de En. de 2024
I have written a code of NDDE, but it is not correct and I am not able to simulate this code, because I am getting errors from it
my code
%% Dynamical System Modeling Using Neural ODE
% Parameters
par = [4; 2; 9.65];
tau = 1;
tau_max = 1.5;
num_trajectories = 5;
T = 30;
% Generating 100 trajectories
colors = jet(num_trajectories);
figure; % Create a single figure
for i = 0:(num_trajectories - 1)
c = 0.5 + i/99;
phi = @(t) c * ones(size(t));
g = @(t, y, Z) par(1) * Z / (1 + Z^par(3)) - par(2) * y;
% Solve the DDE using dde23 for baseline data
sol = dde23(@(t, y, Z) g(t, y, Z), tau, phi, [0 T]);
% Plot the current trajectory on the same figure
plot(sol.x, sol.y, 'Color', colors(i+1, :));
hold on;
end
title('Mackey-Glass Equation Trajectories');
xlabel('Time');
ylabel('x(t)');
hold off
numTimeSteps = 1000;
t = linspace(0, T, numTimeSteps);
X=deval(sol,t);
X_delay=interp1(t,X,t-tau);
xTrain = X(1,:)'; % Transpose to match your shape
% Plot x vs. delayed term
figure;
plot(X(1, :), X_delay);
xlabel('x(t)');
ylabel('x(t-\tau)');
title('x vs. delayed term');
grid on;
neuralOdeTimesteps = 10;
dt = t(2);
timesteps = (0:neuralOdeTimesteps)*dt;
nd=1;
tau = dlarray(tau_max*rand(1,nd));
nx = 1;
hiddenSize = 5;
% output_size = 1;
NDDE = struct;
NDDE.fc1 = struct;
sz = [hiddenSize nx*(1+nd)];
NDDE.fc1.Weights = initializeGlorot(sz);
NDDE.fc1.Bias = initializeZeros([sz(1) 1]);
NDDE.fc2 = struct;
sz = [hiddenSize hiddenSize];
NDDE.fc2.Weights = initializeGlorot(sz);
NDDE.fc2.Bias = initializeZeros([sz(1) 1]);
NDDE.fc3 = struct;
sz = [nx hiddenSize];
NDDE.fc3.Weights = initializeGlorot(sz);
tau = min(max(1e-5,tau),tau_max-1e-5);
gradDecay = 0.9;
sqGradDecay = 0.999;
learnRate = 0.002;
numIter = 1200;
miniBatchSize = 200;
plotFrequency = 10;
averageGrad_p = [];
averageSqGrad_p = [];
monitor = trainingProgressMonitor(Metrics="Loss",Info=["Iteration","LearnRate"],XLabel="Iteration");
numTrainingTimesteps = numTimeSteps;
trainingTimesteps = 1:numTrainingTimesteps;
plottingTimesteps = 2:numTimeSteps;
iteration = 0;
while iteration < numIter && ~monitor.Stop
iteration = iteration + 1;
% Create batch
[X, targets] = createMiniBatch(numTrainingTimesteps, neuralOdeTimesteps, miniBatchSize, xTrain);
% Evaluate network and compute loss and gradients
[loss,grad_par,grad_tau] = dlfeval(@modelLoss,timesteps,X,par,targets);
% Update network
[par,averageGrad_p,averageSqGrad_p] = adamupdate(par,grad_par,averageGrad_p,averageSqGrad_p,iteration, learnRate,gradDecay,sqGradDecay);
[tau,averageGrad_t,averageSqGrad_t] = adamupdate(tau,grad_tau,averageGrad_t,averageSqGrad_t,iteration, learnRate,gradDecay,sqGradDecay);
% Plot loss
recordMetrics(monitor,iteration,Loss=loss);
% Plot predicted vs. real dynamics
if mod(iteration,plotFrequency) == 0 || iteration == 1
% Use ode45 to compute the solution
y=dde23(fun,par,delay,hist,time);
plot(xTrain(1,plottingTimesteps),xTrain(2,plottingTimesteps),"r--")
hold on
plot(y(1,:),y(2,:),"b-")
hold off
xlabel("x(1)")
ylabel("x(2)")
title("Predicted vs. Real Dynamics")
legend("Training Ground Truth", "Predicted")
drawnow
end
updateInfo(monitor,Iteration=iteration,LearnRate=learnRate);
monitor.Progress = 100*iteration/numIter;
end
function X = model(fun,par,delay,hist,time)
X = dde23(fun,par,delay,hist,time);
end
function dx=fun(t,y,Z,par)
dx = par.fc3.Weights*tanh(par.fc2.Weights*tanh(par.fc1.Weights*[y;Z]+par.fc1.Bias)+par.fc2.Bias);
end
function [loss,grad_par,grad_tau] = modelLoss(tspan,X0,par,targets)
% % Compute predictions.
X = model(fun,par,delay,hist,time);
% Compute L1 loss.
loss = l1loss(X,targets);
% Compute gradients.
grad_par = dlgradient(loss,par);
grad_tau = dlgradient(loss,tau);
end
function [x0, targets] = createMiniBatch(numTimesteps,numTimesPerObs,miniBatchSize,X)
% Create batches of trajectories.
s = randperm(numTimesteps - numTimesPerObs, miniBatchSize);
x0 = dlarray(X(s,:));
targets = zeros([size(X,1) miniBatchSize numTimesPerObs]);
for i = 1:miniBatchSize
targets( 1:numTimesPerObs,i) = X( s(i) + 1:(s(i) + numTimesPerObs),:);
end
end
function bias = initializeZeros(sz)
bias = zeros(sz,'single');
bias = dlarray(bias);
end
function weights = initializeGlorot(sz)
Z = 2*rand(sz,'single') - 1;
bound = sqrt(6 / (sz(2)+ sz(1)));
weights = bound * Z;
weights = dlarray(weights);
end
0 comentarios
Respuesta aceptada
Ben
el 5 de En. de 2024
I notice that the model function uses dde23. Unfortunately dde23 is not supported by dlarray and so you can't use this with automatic differentiation. The dlode45 solver is the only ODE solver we have that supports dlarray and automatic differentiation.
It may be possible to work something out with dlode45 but it could be quite complex. For example, for a delay differential equation with 1 delay and for , it's possible to reduce this to an ordinary differential equation for by writing for . Here's a proof of concept using .
p = 0.1;
tau = 1;
phi = @(t) 1;
F = @(t,y,z,p) -y + p*z;
% Solve with dde23 for fixed p on [0,tau]
sol = dde23(@(t,y,z) F(t,y,z,p), tau, phi, [0,tau]);
% Construct equivalent ODE on [0,tau]
G = @(t,y,p) F(t,y,phi(t),p);
% Solve for fixed p
odeSol = ode45(@(t,y) G(t,y,p), [0,tau], phi(0));
% Compute gradients with dlode45
% Here I compute gradients of y(tau) with respect to params as a proof of
% concept.
[y,grad] = dlfeval(@solveAndGradient,G,[0,tau],dlarray(phi(0)),dlarray(p));
function [y,grad] = solveAndGradient(G,tspan,y0,params)
y = dlode45(G,tspan,y0,params,DataFormat="CB");
grad = dlgradient(y,params);
end
To extend beyond would get a little bit complex - potentially you could interpolate the solution on to define for using interp1 (since it is supported by dlarray and automatic differentiation) and use this to solve for for using dlode45. However I expect this could get quite difficult to implement.
Más respuestas (0)
Ver también
Categorías
Más información sobre Sequence and Numeric Feature Data Workflows en Help Center y File Exchange.
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!