Skip to content

Commit 5b4dcb6

Browse files
committed
Interface redesign to include schemes. Minor bugs and enhancements
Bug Fixing: #47 Incorrect computation for dL and dU when K > 0 Enhancements: #12 Vectorize invsatlin function in @hopfieldnetwork class #36 Separate CHN schemes from Simulation functions - HopfieldNetworkGQKP supports 'classic' Scheme only - HopfieldNetworkTSP supports 'classic', 'classic&2opt', 'divide-conquer', 'divide-conquer&2opt' and '2opt #37 Add CheckpointPath support for HopfieldNetworkGQKP #38 Add Runge-Kutta simulation to HopfieldNetworkTSP #39 Add GPU support for all SimFcn methods #40 Allow to provide only V as input to simulation in HopfieldNetworks #41 Compute saddle point in HopfieldNetworkGQKP #42 Compute weights and biases from parameters in HopfieldNetworkGQKP networks #43 Add support for SimulationPlot in HopfieldNetworkGQKP #44 Share CheckpointPath utilities between HopfieldNetworkGQKP and HopfieldNetworkTSP #45 Vectorize simEuler method in HopfieldNetworkTSP #46 SimFcn support in HopfieldNetworkTSP #48 2-opt simulation using 'lin-kernighan' and 'hopfield' Updating release notes.
1 parent 18c081b commit 5b4dcb6

25 files changed

+967
-550
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
function scheme = getScheme(net)
2+
scheme = net.Scheme;
3+
end

chn/+network/@HopfieldNetwork/hopfieldnetwork.m

+5-6
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,8 @@
6464
net = sim(net);
6565
disp(net);
6666
plot(net, varargin);
67+
saddle(net, method);
68+
viewConvergence(iter,V,net);
6769

6870
% --- Set methods --- %
6971
setTrainFcn(net,trainFcn);
@@ -72,29 +74,26 @@
7274
end
7375

7476
methods (Hidden = true, Access = private)
75-
%net = addDefaultOptionValues(net, options);
7677
net = setOptions(net, options);
7778
end
7879

7980
methods (Hidden = false, Access = protected)
8081
net = init(net);
8182
end
8283

83-
% methods (Static = true, Access = public)
84-
% options = createOptions(varargin);
85-
% end
86-
8784
methods (Static = true, Access = protected)
8885
y = satlin(x,u0);
8986
y = invsatlin(x,u0);
9087
end
9188

92-
methods(Access = public) % --- Get-Set methods --- %
89+
% --- Get-Set methods --- %
90+
methods(Access = public)
9391
trainFcn = getTrainFcn(net);
9492
trainParam = getTrainParam(net,field);
9593
setting = getSetting(net,field);
9694
simFcn = getSimFcn(net);
9795
results = getResults(net,field);
96+
scheme = getScheme(net);
9897
setSetting(net,property,value);
9998
setResults(net,property,value);
10099
end
+5-11
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,8 @@
11
function y = invsatlin(x,u0)
22
y = zeros(size(x));
3-
for j = 1:size(x,2)
4-
for i = 1:size(x,1);
5-
if x(i,j) < 0
6-
y(i,j) = u0;
7-
elseif x(i,j) > 1
8-
y(i,j) = -u0;
9-
else
10-
y(i,j) = u0 * (2*x(i,j) - 1);
11-
end
12-
end
13-
end
3+
4+
y(x <= 0) = -u0;
5+
y(x >= 1) = u0;
6+
y(0 < x & x < 1) = u0 .* (2.*x(0 < x & x < 1) - 1);
7+
148
end

chn/+network/@HopfieldNetworkGQKP/HopfieldNetworkGQKP.m

+3-9
Original file line numberDiff line numberDiff line change
@@ -120,18 +120,12 @@
120120

121121
% --- Methods definitions --- %
122122
methods (Hidden = true, Access = private)
123-
%net = addDefaultOptionValues(net, options);
124123
net = setOptions(net,options);
125124
end
126125

127-
% methods (Static = true, Hidden = true, Access = protected)
128-
% % isValidSetting(property,value);
129-
% end
130-
%
131-
% methods (Static = true, Hidden = false, Access = public)
132-
% % options = createOptions(varargin);
133-
% end
134-
126+
methods (Static = true, Hidden = true, Access = private)
127+
128+
end
135129
methods (Hidden = false, Access = protected)
136130
net = init(net);
137131
end
+10
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
function S = saddle(net, method)
2+
3+
method = 'analytic'; % No other method currently supported for HopfieldNetworkGQKP
4+
5+
if ~isfield(net.TrainParam, 'T')
6+
net = train(net);
7+
end
8+
S = -net.TrainParam.T\net.TrainParam.ib;
9+
10+
end

chn/+network/@HopfieldNetworkGQKP/sim.m

+135-39
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,45 @@
1-
function V = sim(net,V,U)
1+
function V = sim(net,V,U,isSaddle)
2+
3+
if nargin == 1 % Start in the center of the Hypercube. Replace for saddle?
4+
U = rand(net.TrainParam.N,1)-.5;
5+
V = 0.5 + 1e-7*U;
6+
elseif nargin == 2
7+
U = net.Setting.InvTransferFcn(V);
8+
end
9+
10+
% Send data to GPU
11+
if strcmp(net.Setting.ExecutionEnvironment,'gpu')
12+
U = gpuArray(U);
13+
V = gpuArray(V);
14+
end
15+
16+
if nargin < 4
17+
isSaddle = false;
18+
end
19+
20+
if ~isSaddle % Logging time and Checkpoint
21+
timeID = tic;
222

3-
timeID = tic;
23+
if ~isempty(net.Setting.CheckpointPath)
24+
net.Results.CheckpointFilename = ...
25+
utils.checkpoint.createFilename(net.Setting.CheckpointPath,net.SimFcn);
26+
else
27+
net.Results.CheckpointFilename = '';
28+
end
29+
end
30+
431
net = reinit(net);
32+
33+
if ~isfield(net.TrainParam,'T')
34+
error('HopfieldNetworkGQKP:NotTrained', 'Training has not taken place yet. Use train(net).');
35+
end
36+
37+
% Classic Scheme support only
538
if strcmp(net.SimFcn,'euler')
6-
if nargin < 2
7-
[net,V,~,iter] = simEuler(net);
8-
else
9-
[net,V,~,iter] = simEuler(net,V,U);
10-
end
39+
[net,V,~,iter] = simEuler(net,V,U,isSaddle);
40+
1141
elseif strcmp(net.SimFcn,'talavan-yanez')
12-
if nargin < 2
13-
[net,V,~,iter] = simTalavanYanez(net);
14-
else
15-
[net,V,~,iter] = simTalavanYanez(net,V,U);
16-
end
42+
[net,V,~,iter] = simTalavanYanez(net,V,U,isSaddle);
1743
end
1844
net = computeSolution(net,V,iter);
1945

@@ -22,8 +48,7 @@
2248

2349

2450
% Euler Algorithm
25-
26-
function [net,V,U,iter] = simEuler(net,V)
51+
function [net,V,U,iter] = simEuler(net,V,U,isSaddle)
2752

2853
% Stopping criteria
2954
stopC1 = power(10, -1 * net.Setting.E);
@@ -38,17 +63,25 @@
3863
% Memory allocation
3964
dU = zeros(N,1);
4065

41-
if nargin == 1
42-
U = rand(N,1)-.5; % TODO Different from Pedro's algorithm
43-
V = 0.5 + 1e-7*U; % TODO Different from Pedro's algorithm
44-
end
45-
4666
iter = 1;
4767
% Showing Network parameters in the command window
4868
% if net.Setting.Verbose
4969
% hopfield.tsp.display.printWhenStarting(net);
5070
% end
5171

72+
if ~isSaddle % Logging Checkpoint and plotting Simulation process
73+
if ~isempty(net.Setting.CheckpointPath) || net.Setting.SimulationPlot
74+
if ~isempty(net.Setting.CheckpointPath)
75+
utils.checkpoint.loggingData(fullfile(net.Setting.CheckpointPath, ...
76+
net.Results.CheckpointFilename),...
77+
net.Setting.MaxIter,iter,V,zeros(size(V)));
78+
end
79+
if net.Setting.SimulationPlot
80+
fV = viewConvergence(iter,V,net);
81+
end
82+
end
83+
end
84+
5285
dt = net.Setting.Dt;
5386
net.Results.Time(iter) = dt;
5487
maxDiffV = 1;
@@ -66,34 +99,60 @@
6699
V = net.Setting.TransferFcn(U);
67100

68101
maxDiffV = max(abs(Vprev-V));
69-
iter = iter + 1;
102+
iter = iter + 1;
103+
104+
if ~isSaddle % Logging Checkpoint and plotting Simulation process
105+
if ~isempty(net.Setting.CheckpointPath) || net.Setting.SimulationPlot
106+
if ~isempty(net.Setting.CheckpointPath)
107+
utils.checkpoint.loggingData(fullfile(net.Setting.CheckpointPath,...
108+
net.Results.CheckpointFilename),...
109+
net.Setting.MaxIter,iter,V,dU);
110+
end
111+
if net.Setting.SimulationPlot
112+
fV = viewConvergence(iter,V,net,fV);
113+
end
114+
end
115+
end
70116
end
117+
118+
if strcmp(net.Setting.ExecutionEnvironment,'gpu') && nargout > 1
119+
V = gather(V);
120+
U = gather(U);
121+
end
122+
123+
if ~isSaddle % Logging Checkpoint
124+
if ~isempty(net.Setting.CheckpointPath)
125+
utils.checkpoint.trimToSimulatedData(net.Setting.CheckpointPath, ...
126+
net.Results.CheckpointFilename, iter)
127+
end
128+
end
129+
71130
net.Results.x = V;
72131
end
73132

74133
% Talaván-Yáñez Algorithm
75134

76-
function [net,V,U,iter] = simTalavanYanez(net,V,U)
77-
135+
function [net,V,U,iter] = simTalavanYanez(net,V,U,isSaddle)
78136

79-
N = net.ProblemParameters.networkSize(1);
80137
T = net.TrainParam.T;
81138
ib = net.TrainParam.ib;
82-
83-
if nargin == 1
84-
U = rand(N,1)-.5; % TODO Different from Pedro's algorithm
85-
V = 0.5 + 1e-7*U; % TODO Different from Pedro's algorithm
86-
end
87-
if strcmp(net.Setting.ExecutionEnvironment,'GPU')
88-
U = gpuArray(U);
89-
V = gpuArray(V);
90-
end
139+
91140
% Stopping criteria
92141
stopC1 = power(10, -1 * net.Setting.E);
93142
stopC2 = power(10, -1.5 * net.Setting.E);
94143
maxDiffV = 1;
95144
unstable = false;
96-
145+
146+
trasferFcn2Str = func2str(net.Setting.TransferFcn);
147+
if strcmp(trasferFcn2Str,'@(u)0.5*(1+tanh(u./net.Setting.U0))')
148+
trasferFcn2Str = 'tanh';
149+
elseif strcmp(trasferFcn2Str,'@(u)net.satlin(u,net.Setting.U0)')
150+
trasferFcn2Str = 'satlin';
151+
else
152+
error('HopfieldNetworkTSP:sim:notDefinedTransferFcn', ...
153+
['TransferFcn derivative not defined for ',net.Setting.TransferFcn]);
154+
end
155+
97156
u_e = net.Setting.InvTransferFcn(stopC1);
98157

99158
iter = 1;
@@ -102,6 +161,19 @@
102161
% hopfield.tsp.display.printWhenStarting(net);
103162
% end
104163

164+
if ~isSaddle % Logging Checkpoint and plotting Simulation process
165+
if ~isempty(net.Setting.CheckpointPath) || net.Setting.SimulationPlot
166+
if ~isempty(net.Setting.CheckpointPath)
167+
utils.checkpoint.loggingData(fullfile(net.Setting.CheckpointPath, ...
168+
net.Results.CheckpointFilename),...
169+
net.Setting.MaxIter,iter,V,zeros(size(V)));
170+
end
171+
if net.Setting.SimulationPlot
172+
fV = viewConvergence(iter,V,net);
173+
end
174+
end
175+
end
176+
105177
while iter < net.Setting.MaxIter && (maxDiffV > stopC1 || ...
106178
(maxDiffV > stopC2 && unstable))
107179

@@ -113,8 +185,12 @@
113185

114186
dU = T*V + ib;
115187

116-
dV = 2./net.Setting.U0 .* V .* (1-V) .*dU;
117-
188+
if strcmp(trasferFcn2Str,'tanh')
189+
dV = 2./net.Setting.U0 .* V .* (1-V) .*dU;
190+
elseif strcmp(trasferFcn2Str,'satlin')
191+
dV = 2./net.Setting.U0 .* dU;
192+
end
193+
118194
interiorV = U > u_e & U < -u_e;
119195

120196
% Computation of dt
@@ -209,7 +285,7 @@
209285

210286
%%%
211287
% $E(t + \Delta t) = E(t) - S_{1}\Delta t + \frac{1}{2}S_{2}\Delta t^{2}$
212-
if strcmp(net.Setting.ExecutionEnvironment,'GPU')
288+
if strcmp(net.Setting.ExecutionEnvironment,'gpu')
213289
S1 = gather(S1);
214290
S2 = gather(S2);
215291
dt = gather(dt);
@@ -218,18 +294,38 @@
218294
S1.*dt + 0.5.*S2.*dt.^2;
219295
net.Results.Time(iter+1) = net.Results.Time(iter) + dt;
220296
iter = iter + 1;
297+
298+
if ~isSaddle % Logging Checkpoint and plotting Simulation process
299+
if ~isempty(net.Setting.CheckpointPath) || net.Setting.SimulationPlot
300+
if ~isempty(net.Setting.CheckpointPath)
301+
utils.checkpoint.loggingData(fullfile(net.Setting.CheckpointPath,...
302+
net.Results.CheckpointFilename),...
303+
net.Setting.MaxIter,iter,V,dU);
304+
end
305+
if net.Setting.SimulationPlot
306+
fV = viewConvergence(iter,V,net,fV);
307+
end
308+
end
309+
end
221310
end
222311

223-
if strcmp(net.Setting.ExecutionEnvironment,'GPU') && nargout > 1
312+
if strcmp(net.Setting.ExecutionEnvironment,'gpu') && nargout > 1
224313
V = gather(V);
225314
U = gather(U);
226-
iter = gather(iter);
227315
end
316+
317+
if ~isSaddle % Logging Checkpoint
318+
if ~isempty(net.Setting.CheckpointPath)
319+
utils.checkpoint.trimToSimulatedData(net.Setting.CheckpointPath, ...
320+
net.Results.CheckpointFilename, iter);
321+
end
322+
end
323+
228324
end
229325

230326
function net = computeSolution(net,V,iter)
231327

232-
V(V > 1 - power(10, -1 * net.Setting.E)) = 1; %FIXME to be removed?
328+
V(V > 1 - power(10, -1 * net.Setting.E)) = 1;
233329
V(V < power(10, -1 * net.Setting.E)) = 0;
234330

235331
if isequal(net.ProblemParameters.R*V,net.ProblemParameters.b)

0 commit comments

Comments
 (0)