22 NN::NN(
int _inputs,
int _hiddens,
int _outputs,
double learnrate)
23 :inputs(_inputs), hiddens(_hiddens), outputs(_outputs)
76 for (
int x = 0; x <
hiddens; x++)
83 for (
int x = 0; x <
hiddens; x++)
85 for (
int y = 0; y <
inputs+1; y++)
92 weights[0][x][y] = ((double)2*random()/RAND_MAX-1)/3;
100 for (
int x = 0; x <
outputs; x++)
106 for (
int x = 0; x <
outputs; x++)
108 for (
int y = 0; y <
hiddens+1; y++)
113 weights[1][x][y] = ((double)2*random()/RAND_MAX-1)/3;
153 for (
int x = 0; x <
hiddens; x++)
155 for (
int y = 0; y <
inputs+1; y++)
161 for (
int x = 0; x <
outputs; x++)
163 for (
int y = 0; y <
hiddens+1; y++)
175 f = fopen(fname,
"r");
180 int finput, fhidden, foutput;
182 int res = fscanf(f,
"NN %f %d %d %d\n", &version, &finput, &fhidden, &foutput);
198 f = fopen(fname,
"r");
201 fprintf(stderr,
"Error: could not load file %s\n", fname);
210 int finput, fhidden, foutput;
212 int res = fscanf(f,
"NN %f %d %d %d\n", &version, &finput, &fhidden, &foutput);
215 printf(
"Error: unrecognized neural network file. Expected header 'NN <version> <inputs> <hidden> <outputs>'.");
220 printf(
"Error: loaded network is %1.2f, but code can only handle %1.2f.",
234 for (
int x = 0; x <
hiddens; x++)
236 for (
int y = 0; y <
inputs+1; y++)
238 fscanf(f,
"%lf", &
weights[0][x][y]);
243 for (
int x = 0; x <
outputs; x++)
245 for (
int y = 0; y <
hiddens+1; y++)
247 fscanf(f,
"%lf ", &
weights[1][x][y]);
257 f = fopen(fname,
"w+");
260 fprintf(stderr,
"Error: could not open file for saving.\n");
270 for (
int x = 0; x <
hiddens; x++)
272 for (
int y = 0; y <
inputs+1; y++)
275 fprintf(f,
"%lf ",
weights[0][x][y]);
280 for (
int x = 0; x <
outputs; x++)
282 for (
int y = 0; y <
hiddens+1; y++)
285 fprintf(f,
"%lf ",
weights[1][x][y]);
294 return (1/(1+exp(-a)));
303 double NN::outputerr(
const std::vector<double> &out,
const std::vector<double> &expected,
int which)
305 double err = (expected[which]-out[which]);
307 err *=
dg(out[which]);
312 double NN::internalerr(
const std::vector<double> &out,
const std::vector<double> &expected,
int which)
316 for (
int x = 0; x <
outputs; x++)
327 for (
int x = 0; x <
outputs; x++)
335 double answer = 0, t;
336 for (
int x = 0; x <
outputs; x++)
338 t = (
output[x]-target[x]);
344 double NN::train(std::vector<double> &input, std::vector<double> &target)
349 for (
int x = 0; x <
outputs; x++)
352 errors[1][x][0] = xoutputerror;
354 for (
int y = 0; y <
hiddens; y++)
362 for (
int x = 0; x <
hiddens; x++)
365 errors[0][x][0] = xinternalerror;
367 for (
int y = 0; y <
inputs; y++)
369 errors[0][x][y+1] = input[y]*xinternalerror;
374 return error(target);
377 double NN::train(std::vector<unsigned int> &input, std::vector<double> &target)
379 assert(!
"Code needs updating");
383 for (
int x = 0; x <
outputs; x++)
386 errors[1][x][0] = xoutputerror;
388 for (
int y = 0; y <
hiddens; y++)
396 for (
int x = 0; x <
hiddens; x++)
399 errors[0][x][0] = xinternalerror;
401 for (
unsigned int y = 0; y < input.size(); y++)
403 errors[0][x][input[y]+1] = (1)*xinternalerror;
407 return error(target);
413 double NN::GetInput(std::vector<double> &input,
const std::vector<double> &target)
418 for (
int x = 0; x <
hiddens; x++)
421 for (
int y = 0; y <
inputs; y++)
423 input[y] +=
weights[0][x][y+1]*xinternalerror;
426 return error(target);
432 for (
int y = 0; y <
hiddens; y++)
435 for (
int x = 0; x <
inputs; x++)
437 for (
int y = 0; y <
hiddens; y++)
441 for (
int y = 0; y <
hiddens; y++)
444 for (
int y = 0; y <
outputs; y++)
448 for (
int x = 0; x <
hiddens; x++)
466 double *
NN::test(
const std::vector<unsigned int> &input)
469 for (
int y = 0; y <
hiddens; y++)
472 for (
unsigned int x = 0; x < input.size(); x++)
473 for (
int y = 0; y <
hiddens; y++)
477 for (
int y = 0; y <
hiddens; y++)
480 for (
int y = 0; y <
outputs; y++)
484 for (
int x = 0; x <
hiddens; x++)
504 cout <<
"Neural network weights:" << endl;
505 for (
int x = 0; x <
outputs; x++)
507 cout <<
"Input weights to output " << x <<
":";
508 for (
int y = 0; y <
hiddens+1; y++)
509 cout <<
" " <<
weights[1][x][y];
512 for (
int x = 0; x <
outputs; x++)
514 cout <<
"Input weights to hidden node " << x <<
":";
515 for (
int y = 0; y <
hiddens+1; y++)
516 cout <<
" " <<
weights[0][x][y];