1 /**********************************************************************
2   ga_utility.c
3  **********************************************************************
4 
5   ga_utility - High-level genetic algorithm routines.
6   Copyright ©2000-2005, Stewart Adcock <stewart@linux-domain.com>
7   All rights reserved.
8 
9   The latest version of this program should be available at:
10   http://gaul.sourceforge.net/
11 
12   This program is free software; you can redistribute it and/or modify
13   it under the terms of the GNU General Public License as published by
14   the Free Software Foundation; either version 2 of the License, or
15   (at your option) any later version.  Alternatively, if your project
16   is incompatible with the GPL, I will probably agree to requests
17   for permission to use the terms of any other license.
18 
19   This program is distributed in the hope that it will be useful, but
20   WITHOUT ANY WARRANTY WHATSOEVER.
21 
22   A full copy of the GNU General Public License should be in the file
23   "COPYING" provided with this distribution; if not, see:
24   http://www.gnu.org/
25 
26  **********************************************************************
27 
28   Synopsis:     High-level GA functions and convenience functions.
29 
30   To do:	Population/entity iterator functions.
31 		On-line and off-line performance summaries.
32 
33  **********************************************************************/
34 
35 #include "gaul.h"
36 
37 
38 /**********************************************************************
39   ga_diagnostics()
40   synopsis:	Display diagnostics message.
41   parameters:	none
42   return:	none
43   last updated:	17 Feb 2005
44  **********************************************************************/
45 
ga_diagnostics(void)46 void ga_diagnostics(void)
47   {
48   int	num_pops;	/* Number of populations defined, or -1 for no table. */
49 
50   printf("=== GA utility library =======================================\n");
51   printf("Version:                     %s\n", GA_VERSION_STRING);
52   printf("Build date:                  %s\n", GA_BUILD_DATE_STRING);
53   printf("Compilation machine characteristics:\n%s\n", GA_UNAME_STRING);
54   printf("--- Constants ------------------------------------------------\n");
55   printf("GA_DEBUG:                    %d\n", GA_DEBUG);
56   printf("GA_BOLTZMANN_FACTOR:         %e\n", GA_BOLTZMANN_FACTOR);
57   printf("GA_MIN_FITNESS:              %e\n", GA_MIN_FITNESS);
58   printf("BYTEBITS:                    %d\n", BYTEBITS);
59   printf("--- Defaults -------------------------------------------------\n");
60   printf("GA_DEFAULT_CROSSOVER_RATIO:  %f\n", GA_DEFAULT_CROSSOVER_RATIO);
61   printf("GA_DEFAULT_MUTATION_RATIO:   %f\n", GA_DEFAULT_MUTATION_RATIO);
62   printf("GA_DEFAULT_MIGRATION_RATIO:  %f\n", GA_DEFAULT_MIGRATION_RATIO);
63   printf("GA_DEFAULT_ALLELE_MUTATION_PROB: %f\n", GA_DEFAULT_ALLELE_MUTATION_PROB);
64   printf("--- Data structures ------------------------------------------\n");
65   printf("structure                    sizeof\n");
66   printf("population                   %lu\n", (unsigned long) sizeof(population));
67   printf("entity                       %lu\n", (unsigned long) sizeof(entity));
68   printf("byte                         %lu\n", (unsigned long) sizeof(byte));
69   printf("--- Current variables ----------------------------------------\n");
70   num_pops = ga_get_num_populations();
71   if (num_pops==-1)
72     {
73     printf("Population table:            undefined\n");
74     }
75   else
76     {
77     printf("Population table:            defined\n");
78     printf("Size:                        %d\n", num_pops);
79     }
80   printf("==============================================================\n");
81 
82   return;
83   }
84 
85 /**********************************************************************
86   ga_get_major_version()
87   synopsis:	Return major version number.
88   parameters:	none
89   return:	none
90   last updated:	06 Apr 2003
91  **********************************************************************/
92 
ga_get_major_version(void)93 int ga_get_major_version( void )
94   {
95 
96   return GA_MAJOR_VERSION;
97   }
98 
99 
100 /**********************************************************************
101   ga_get_minor_version()
102   synopsis:	Return major version number.
103   parameters:	none
104   return:	none
105   last updated:	06 Apr 2003
106  **********************************************************************/
107 
ga_get_minor_version(void)108 int ga_get_minor_version( void )
109   {
110 
111   return GA_MINOR_VERSION;
112   }
113 
114 
115 /**********************************************************************
116   ga_get_patch_version()
117   synopsis:	Return patch level (version) number.
118   parameters:	none
119   return:	none
120   last updated:	06 Apr 2003
121  **********************************************************************/
122 
ga_get_patch_version(void)123 int ga_get_patch_version( void )
124   {
125 
126   return GA_PATCH_VERSION;
127   }
128 
129 
130 /**********************************************************************
131   ga_genesis_integer()
132   synopsis:	High-level function to create a new population and
133 		perform the basic setup (i.e. initial seeding) required
134 		for further optimisation and manipulation.
135 		Assumes the use of integer chromosomes is desired.
136 		Integer-valued chromsomes.
137   parameters:
138   return:	population, or NULL on failure.
139   last updated:	17 Feb 2005
140  **********************************************************************/
141 
ga_genesis_integer(const int population_size,const int num_chromo,const int len_chromo,GAgeneration_hook generation_hook,GAiteration_hook iteration_hook,GAdata_destructor data_destructor,GAdata_ref_incrementor data_ref_incrementor,GAevaluate evaluate,GAseed seed,GAadapt adapt,GAselect_one select_one,GAselect_two select_two,GAmutate mutate,GAcrossover crossover,GAreplace replace,vpointer userdata)142 population *ga_genesis_integer(	const int		population_size,
143 			const int		num_chromo,
144 			const int		len_chromo,
145 			GAgeneration_hook	generation_hook,
146 			GAiteration_hook	iteration_hook,
147 			GAdata_destructor	data_destructor,
148 			GAdata_ref_incrementor	data_ref_incrementor,
149 			GAevaluate		evaluate,
150 			GAseed			seed,
151 			GAadapt			adapt,
152 			GAselect_one		select_one,
153 			GAselect_two		select_two,
154 			GAmutate		mutate,
155 			GAcrossover		crossover,
156 			GAreplace		replace,
157 			vpointer		userdata )
158   {
159   population	*pop;	/* The new population structure. */
160 
161   plog(LOG_VERBOSE, "Genesis is beginning!");
162 
163 /*
164  * Initialise OpenMP code.
165  */
166   ga_init_openmp();
167 
168 /*
169  * Allocate and initialise a new population.
170  * This call also sets this as the active population.
171  */
172   if ( !(pop = ga_population_new( population_size, num_chromo, len_chromo )) )
173     return NULL;
174 
175 /*
176  * Assign population's user data.
177  */
178   pop->data = userdata;
179 
180 /*
181  * Define some callback functions.
182  */
183   pop->generation_hook = generation_hook;
184   pop->iteration_hook = iteration_hook;
185 
186   pop->data_destructor = data_destructor;
187   pop->data_ref_incrementor = data_ref_incrementor;
188 
189   pop->chromosome_constructor = ga_chromosome_integer_allocate;
190   pop->chromosome_destructor = ga_chromosome_integer_deallocate;
191   pop->chromosome_replicate = ga_chromosome_integer_replicate;
192   pop->chromosome_to_bytes = ga_chromosome_integer_to_bytes;
193   pop->chromosome_from_bytes = ga_chromosome_integer_from_bytes;
194   pop->chromosome_to_string = ga_chromosome_integer_to_string;
195 
196   pop->evaluate = evaluate;
197   pop->seed = seed;
198   pop->adapt = adapt;
199   pop->select_one = select_one;
200   pop->select_two = select_two;
201   pop->mutate = mutate;
202   pop->crossover = crossover;
203   pop->replace = replace;
204 
205 /*
206  * Seed the population.
207  */
208 #if 0
209   if (seed==NULL)
210     {
211     plog(LOG_VERBOSE, "Entity seed function not defined.  Genesis can not occur.  Continuing anyway.");
212     }
213   else
214     {
215     ga_population_seed(pop);
216     plog(LOG_VERBOSE, "Genesis has occured!");
217     }
218 #endif
219 
220   return pop;
221   }
222 
223 
224 /**********************************************************************
225   ga_genesis() and ga_genesis_int()
226   *** DEPRECATED FUNCTIONS! ***
227   synopsis:	High-level function to create a new population and
228 		perform the basic setup (i.e. initial seeding) required
229 		for further optimisation and manipulation.
230 		Assumes the use of integer chromosomes is desired.
231 		This currently only exists for compatibility with
232 		older versions of GAUL.
233 		Integer-valued chromsomes.
234   parameters:
235   return:	population, or NULL on failure.
236   last updated:	25 Mar 2004
237  **********************************************************************/
238 
239 #ifndef COMPILE_DEPRECATED_FUNCTIONS
240 
ga_genesis(const int population_size,const int num_chromo,const int len_chromo,GAgeneration_hook generation_hook,GAiteration_hook iteration_hook,GAdata_destructor data_destructor,GAdata_ref_incrementor data_ref_incrementor,GAevaluate evaluate,GAseed seed,GAadapt adapt,GAselect_one select_one,GAselect_two select_two,GAmutate mutate,GAcrossover crossover,GAreplace replace,vpointer userdata)241 population *ga_genesis(	const int		population_size,
242 			const int		num_chromo,
243 			const int		len_chromo,
244 			GAgeneration_hook	generation_hook,
245 			GAiteration_hook	iteration_hook,
246 			GAdata_destructor	data_destructor,
247 			GAdata_ref_incrementor	data_ref_incrementor,
248 			GAevaluate		evaluate,
249 			GAseed			seed,
250 			GAadapt			adapt,
251 			GAselect_one		select_one,
252 			GAselect_two		select_two,
253 			GAmutate		mutate,
254 			GAcrossover		crossover,
255 			GAreplace		replace,
256 			vpointer		userdata )
257   {
258   plog(LOG_FIXME, "Use of ga_genesis() is deprecated.  Modify code to use ga_genesis_integer() instead.");
259 
260   return ga_genesis_integer( population_size, num_chromo, len_chromo,
261                              generation_hook, iteration_hook,
262                              data_destructor, data_ref_incrementor,
263                              evaluate, seed, adapt,
264                              select_one, select_two, mutate, crossover, replace,
265                              userdata );
266   }
267 
ga_genesis_int(const int population_size,const int num_chromo,const int len_chromo,GAgeneration_hook generation_hook,GAiteration_hook iteration_hook,GAdata_destructor data_destructor,GAdata_ref_incrementor data_ref_incrementor,GAevaluate evaluate,GAseed seed,GAadapt adapt,GAselect_one select_one,GAselect_two select_two,GAmutate mutate,GAcrossover crossover,GAreplace replace,vpointer userdata)268 population *ga_genesis_int(	const int		population_size,
269 			const int		num_chromo,
270 			const int		len_chromo,
271 			GAgeneration_hook	generation_hook,
272 			GAiteration_hook	iteration_hook,
273 			GAdata_destructor	data_destructor,
274 			GAdata_ref_incrementor	data_ref_incrementor,
275 			GAevaluate		evaluate,
276 			GAseed			seed,
277 			GAadapt			adapt,
278 			GAselect_one		select_one,
279 			GAselect_two		select_two,
280 			GAmutate		mutate,
281 			GAcrossover		crossover,
282 			GAreplace		replace,
283 			vpointer		userdata )
284   {
285   plog(LOG_FIXME, "Use of ga_genesis_int() is deprecated.  Modify code to use ga_genesis_integer() instead.");
286 
287   return ga_genesis_integer( population_size, num_chromo, len_chromo,
288                              generation_hook, iteration_hook,
289                              data_destructor, data_ref_incrementor,
290                              evaluate, seed, adapt,
291                              select_one, select_two, mutate, crossover, replace,
292                              userdata );
293   }
294 #endif
295 
296 
297 /**********************************************************************
298   ga_genesis_char()
299   synopsis:	High-level function to create a new population and
300 		perform the basic setup (i.e. initial seeding) required
301 		for further optimisation and manipulation.
302 		Character-valued chromosomes.
303   parameters:
304   return:	population, or NULL on failure.
305   last updated:	17 Feb 2005
306  **********************************************************************/
307 
ga_genesis_char(const int population_size,const int num_chromo,const int len_chromo,GAgeneration_hook generation_hook,GAiteration_hook iteration_hook,GAdata_destructor data_destructor,GAdata_ref_incrementor data_ref_incrementor,GAevaluate evaluate,GAseed seed,GAadapt adapt,GAselect_one select_one,GAselect_two select_two,GAmutate mutate,GAcrossover crossover,GAreplace replace,vpointer userdata)308 population *ga_genesis_char(	const int		population_size,
309 			const int		num_chromo,
310 			const int		len_chromo,
311 			GAgeneration_hook	generation_hook,
312 			GAiteration_hook	iteration_hook,
313 			GAdata_destructor	data_destructor,
314 			GAdata_ref_incrementor	data_ref_incrementor,
315 			GAevaluate		evaluate,
316 			GAseed			seed,
317 			GAadapt			adapt,
318 			GAselect_one		select_one,
319 			GAselect_two		select_two,
320 			GAmutate		mutate,
321 			GAcrossover		crossover,
322 			GAreplace		replace,
323 			vpointer		userdata )
324   {
325   population	*pop;	/* The new population structure. */
326 
327   plog(LOG_VERBOSE, "Genesis is beginning!");
328 
329 /*
330  * Initialise OpenMP code.
331  */
332   ga_init_openmp();
333 
334 /*
335  * Allocate and initialise a new population.
336  * This call also sets this as the active population.
337  */
338   if ( !(pop = ga_population_new( population_size, num_chromo, len_chromo )) )
339     return NULL;
340 
341 /*
342  * Assign population's user data.
343  */
344   pop->data = userdata;
345 
346 /*
347  * Define some callback functions.
348  */
349   pop->generation_hook = generation_hook;
350   pop->iteration_hook = iteration_hook;
351 
352   pop->data_destructor = data_destructor;
353   pop->data_ref_incrementor = data_ref_incrementor;
354 
355   pop->chromosome_constructor = ga_chromosome_char_allocate;
356   pop->chromosome_destructor = ga_chromosome_char_deallocate;
357   pop->chromosome_replicate = ga_chromosome_char_replicate;
358   pop->chromosome_to_bytes = ga_chromosome_char_to_bytes;
359   pop->chromosome_from_bytes = ga_chromosome_char_from_bytes;
360   pop->chromosome_to_string = ga_chromosome_char_to_string;
361 
362   pop->evaluate = evaluate;
363   pop->seed = seed;
364   pop->adapt = adapt;
365   pop->select_one = select_one;
366   pop->select_two = select_two;
367   pop->mutate = mutate;
368   pop->crossover = crossover;
369   pop->replace = replace;
370 
371 /*
372  * Seed the population.
373  */
374 #if 0
375   if (seed==NULL)
376     {
377     plog(LOG_VERBOSE, "Entity seed function not defined.  Genesis can not occur.  Continuing anyway.");
378     }
379   else
380     {
381     ga_population_seed(pop);
382     plog(LOG_VERBOSE, "Genesis has occured!");
383     }
384 #endif
385 
386   return pop;
387   }
388 
389 
390 /**********************************************************************
391   ga_genesis_boolean()
392   synopsis:	High-level function to create a new population and
393 		perform the basic setup (i.e. initial seeding) required
394 		for further optimisation and manipulation.
395 		Boolean-valued chromosomes.
396   parameters:
397   return:	population, or NULL on failure.
398   last updated:	17 Feb 2005
399  **********************************************************************/
400 
ga_genesis_boolean(const int population_size,const int num_chromo,const int len_chromo,GAgeneration_hook generation_hook,GAiteration_hook iteration_hook,GAdata_destructor data_destructor,GAdata_ref_incrementor data_ref_incrementor,GAevaluate evaluate,GAseed seed,GAadapt adapt,GAselect_one select_one,GAselect_two select_two,GAmutate mutate,GAcrossover crossover,GAreplace replace,vpointer userdata)401 population *ga_genesis_boolean(	const int		population_size,
402 			const int		num_chromo,
403 			const int		len_chromo,
404 			GAgeneration_hook	generation_hook,
405 			GAiteration_hook	iteration_hook,
406 			GAdata_destructor	data_destructor,
407 			GAdata_ref_incrementor	data_ref_incrementor,
408 			GAevaluate		evaluate,
409 			GAseed			seed,
410 			GAadapt			adapt,
411 			GAselect_one		select_one,
412 			GAselect_two		select_two,
413 			GAmutate		mutate,
414 			GAcrossover		crossover,
415 			GAreplace		replace,
416 			vpointer		userdata )
417   {
418   population	*pop;	/* The new population structure. */
419 
420   plog(LOG_VERBOSE, "Genesis is beginning!");
421 
422 /*
423  * Initialise OpenMP code.
424  */
425   ga_init_openmp();
426 
427 /*
428  * Allocate and initialise a new population.
429  * This call also sets this as the active population.
430  */
431   if ( !(pop = ga_population_new( population_size, num_chromo, len_chromo )) )
432     return NULL;
433 
434 /*
435  * Assign population's user data.
436  */
437   pop->data = userdata;
438 
439 /*
440  * Define some callback functions.
441  */
442   pop->generation_hook = generation_hook;
443   pop->iteration_hook = iteration_hook;
444 
445   pop->data_destructor = data_destructor;
446   pop->data_ref_incrementor = data_ref_incrementor;
447 
448   pop->chromosome_constructor = ga_chromosome_boolean_allocate;
449   pop->chromosome_destructor = ga_chromosome_boolean_deallocate;
450   pop->chromosome_replicate = ga_chromosome_boolean_replicate;
451   pop->chromosome_to_bytes = ga_chromosome_boolean_to_bytes;
452   pop->chromosome_from_bytes = ga_chromosome_boolean_from_bytes;
453   pop->chromosome_to_string = ga_chromosome_boolean_to_string;
454 
455   pop->evaluate = evaluate;
456   pop->seed = seed;
457   pop->adapt = adapt;
458   pop->select_one = select_one;
459   pop->select_two = select_two;
460   pop->mutate = mutate;
461   pop->crossover = crossover;
462   pop->replace = replace;
463 
464 /*
465  * Seed the population.
466  */
467 #if 0
468   if (seed==NULL)
469     {
470     plog(LOG_VERBOSE, "Entity seed function not defined.  Genesis can not occur.  Continuing anyway.");
471     }
472   else
473     {
474     ga_population_seed(pop);
475     plog(LOG_VERBOSE, "Genesis has occured!");
476     }
477 #endif
478 
479   return pop;
480   }
481 
482 
483 /**********************************************************************
484   ga_genesis_double()
485   synopsis:	High-level function to create a new population and
486 		perform the basic setup (i.e. initial seeding) required
487 		for further optimisation and manipulation.
488 		Double precision real-valued chromosomes.
489   parameters:
490   return:	population, or NULL on failure.
491   last updated:	17 Feb 2005
492  **********************************************************************/
493 
ga_genesis_double(const int population_size,const int num_chromo,const int len_chromo,GAgeneration_hook generation_hook,GAiteration_hook iteration_hook,GAdata_destructor data_destructor,GAdata_ref_incrementor data_ref_incrementor,GAevaluate evaluate,GAseed seed,GAadapt adapt,GAselect_one select_one,GAselect_two select_two,GAmutate mutate,GAcrossover crossover,GAreplace replace,vpointer userdata)494 population *ga_genesis_double(	const int		population_size,
495 			const int		num_chromo,
496 			const int		len_chromo,
497 			GAgeneration_hook	generation_hook,
498 			GAiteration_hook	iteration_hook,
499 			GAdata_destructor	data_destructor,
500 			GAdata_ref_incrementor	data_ref_incrementor,
501 			GAevaluate		evaluate,
502 			GAseed			seed,
503 			GAadapt			adapt,
504 			GAselect_one		select_one,
505 			GAselect_two		select_two,
506 			GAmutate		mutate,
507 			GAcrossover		crossover,
508 			GAreplace		replace,
509 			vpointer		userdata )
510   {
511   population	*pop;	/* The new population structure. */
512 
513   plog(LOG_VERBOSE, "Genesis is beginning!");
514 
515 /*
516  * Initialise OpenMP code.
517  */
518   ga_init_openmp();
519 
520 /*
521  * Allocate and initialise a new population.
522  * This call also sets this as the active population.
523  */
524   if ( !(pop = ga_population_new( population_size, num_chromo, len_chromo )) )
525     return NULL;
526 
527 /*
528  * Assign population's user data.
529  */
530   pop->data = userdata;
531 
532 /*
533  * Define some callback functions.
534  */
535   pop->generation_hook = generation_hook;
536   pop->iteration_hook = iteration_hook;
537 
538   pop->data_destructor = data_destructor;
539   pop->data_ref_incrementor = data_ref_incrementor;
540 
541   pop->chromosome_constructor = ga_chromosome_double_allocate;
542   pop->chromosome_destructor = ga_chromosome_double_deallocate;
543   pop->chromosome_replicate = ga_chromosome_double_replicate;
544   pop->chromosome_to_bytes = ga_chromosome_double_to_bytes;
545   pop->chromosome_from_bytes = ga_chromosome_double_from_bytes;
546   pop->chromosome_to_string = ga_chromosome_double_to_string;
547 
548   pop->evaluate = evaluate;
549   pop->seed = seed;
550   pop->adapt = adapt;
551   pop->select_one = select_one;
552   pop->select_two = select_two;
553   pop->mutate = mutate;
554   pop->crossover = crossover;
555   pop->replace = replace;
556 
557 /*
558  * Seed the population.
559  */
560 #if 0
561   if (seed==NULL)
562     {
563     plog(LOG_VERBOSE, "Entity seed function not defined.  Genesis can not occur.  Continuing anyway.");
564     }
565   else
566     {
567     ga_population_seed(pop);
568     plog(LOG_VERBOSE, "Genesis has occured!");
569     }
570 #endif
571 
572   return pop;
573   }
574 
575 
576 /**********************************************************************
577   ga_genesis_bitstring()
578   synopsis:	High-level function to create a new population and
579 		perform the basic setup (i.e. initial seeding) required
580 		for further optimisation and manipulation.
581 		Bitstring-valued chromosomes.
582   parameters:
583   return:	population, or NULL on failure.
584   last updated:	17 Feb 2005
585  **********************************************************************/
586 
ga_genesis_bitstring(const int population_size,const int num_chromo,const int len_chromo,GAgeneration_hook generation_hook,GAiteration_hook iteration_hook,GAdata_destructor data_destructor,GAdata_ref_incrementor data_ref_incrementor,GAevaluate evaluate,GAseed seed,GAadapt adapt,GAselect_one select_one,GAselect_two select_two,GAmutate mutate,GAcrossover crossover,GAreplace replace,vpointer userdata)587 population *ga_genesis_bitstring(	const int		population_size,
588 			const int		num_chromo,
589 			const int		len_chromo,
590 			GAgeneration_hook	generation_hook,
591 			GAiteration_hook	iteration_hook,
592 			GAdata_destructor	data_destructor,
593 			GAdata_ref_incrementor	data_ref_incrementor,
594 			GAevaluate		evaluate,
595 			GAseed			seed,
596 			GAadapt			adapt,
597 			GAselect_one		select_one,
598 			GAselect_two		select_two,
599 			GAmutate		mutate,
600 			GAcrossover		crossover,
601 			GAreplace		replace,
602 			vpointer		userdata )
603   {
604   population	*pop;	/* The new population structure. */
605 
606   plog(LOG_VERBOSE, "Genesis is beginning!");
607 
608 /*
609  * Initialise OpenMP code.
610  */
611   ga_init_openmp();
612 
613 /*
614  * Allocate and initialise a new population.
615  * This call also sets this as the active population.
616  */
617   if ( !(pop = ga_population_new( population_size, num_chromo, len_chromo )) )
618     return NULL;
619 
620 /*
621  * Assign population's user data.
622  */
623   pop->data = userdata;
624 
625 /*
626  * Define some callback functions.
627  */
628   pop->generation_hook = generation_hook;
629   pop->iteration_hook = iteration_hook;
630 
631   pop->data_destructor = data_destructor;
632   pop->data_ref_incrementor = data_ref_incrementor;
633 
634   pop->chromosome_constructor = ga_chromosome_bitstring_allocate;
635   pop->chromosome_destructor = ga_chromosome_bitstring_deallocate;
636   pop->chromosome_replicate = ga_chromosome_bitstring_replicate;
637   pop->chromosome_to_bytes = ga_chromosome_bitstring_to_bytes;
638   pop->chromosome_from_bytes = ga_chromosome_bitstring_from_bytes;
639   pop->chromosome_to_string = ga_chromosome_bitstring_to_string;
640 
641   pop->evaluate = evaluate;
642   pop->seed = seed;
643   pop->adapt = adapt;
644   pop->select_one = select_one;
645   pop->select_two = select_two;
646   pop->mutate = mutate;
647   pop->crossover = crossover;
648   pop->replace = replace;
649 
650 /*
651  * Seed the population.
652  */
653 #if 0
654   if (seed==NULL)
655     {
656     plog(LOG_VERBOSE, "Entity seed function not defined.  Genesis can not occur.  Continuing anyway.");
657     }
658   else
659     {
660     ga_population_seed(pop);
661     plog(LOG_VERBOSE, "Genesis has occured!");
662     }
663 #endif
664 
665   return pop;
666   }
667 
668 
669 /**********************************************************************
670   ga_allele_search()
671   synopsis:	Perform complete systematic search on a given allele
672 		in a given entity.  If initial solution is NULL, then
673 		a random solution is generated (but use of that feature
674 		is unlikely to be useful!).
675 		The original entity will not be munged.
676                 NOTE: max_val is the maximum value _+_ 1!
677 		WARNING: Now only works for integer array chromosomes!
678 		FIXME: Need to make chromosome datatype agnostic.
679   parameters:
680   return:	Best solution found.
681   last updated:	24/03/01
682  **********************************************************************/
683 
684 #ifndef COMPILE_DEPRECATED_FUNCTIONS
685 
ga_allele_search(population * pop,const int chromosomeid,const int point,const int min_val,const int max_val,entity * initial)686 entity *ga_allele_search(	population	*pop,
687 				const int	chromosomeid,
688 				const int	point,
689 				const int 	min_val,
690 				const int 	max_val,
691 				entity		*initial )
692   {
693   int		val;			/* Current value for point. */
694   entity	*current, *best;	/* The solutions. */
695 
696 /* Checks. */
697 /* FIXME: More checks needed. */
698   if ( !pop ) die("Null pointer to population structure passed.");
699 
700   current = ga_get_free_entity(pop);	/* The 'working' solution. */
701   best = ga_get_free_entity(pop);	/* The best solution so far. */
702 
703   plog(LOG_WARNING, "ga_allele_search() is a deprecated function!");
704 
705 /* Do we need to generate a random solution? */
706   if (initial==NULL)
707     {
708     plog(LOG_VERBOSE, "Will perform systematic allele search with random starting solution.");
709 
710     pop->seed(pop, best);
711     }
712   else
713     {
714     plog(LOG_VERBOSE, "Will perform systematic allele search.");
715 
716     ga_entity_copy(pop, best, initial);
717     }
718 
719 /*
720  * Copy best solution over current solution.
721  */
722   ga_entity_copy(pop, current, best);
723   best->fitness=GA_MIN_FITNESS;
724 
725 /*
726  * Loop over the range of legal values.
727  */
728   for (val = min_val; val < max_val; val++)
729     {
730     ((int *)current->chromosome[chromosomeid])[point] = val;
731     ga_entity_clear_data(pop, current, chromosomeid);
732 
733     pop->evaluate(pop, current);
734 
735 /*
736  * Should we keep this solution?
737  */
738     if ( best->fitness < current->fitness )
739       { /* Copy this solution best solution. */
740       ga_entity_blank(pop, best);
741       ga_entity_copy(pop, best, current);
742       }
743     else
744       { /* Copy best solution over current solution. */
745       ga_entity_blank(pop, current);
746       ga_entity_copy(pop, current, best);
747       }
748 
749     }
750 
751   plog(LOG_VERBOSE,
752             "After complete search the best solution has fitness score of %f",
753             best->fitness );
754 
755 /*
756  * Current no longer needed.  It is upto the caller to dereference the
757  * optimum solution found.
758  */
759   ga_entity_dereference(pop, current);
760 
761   return best;
762   }
763 #endif
764 
765 
766 /**********************************************************************
767   ga_population_dump()
768   synopsis:	Dump some statistics about a population.
769   parameters:	population	*pop
770   return:	none
771   last updated:	17 Feb 2005
772  **********************************************************************/
773 
ga_population_dump(population * pop)774 void ga_population_dump(population	*pop)
775   {
776   printf("Population id %d\n", (int) ga_get_population_id(pop));
777   printf("Max size %d Stable size %d Current size %d\n", pop->max_size, pop->stable_size, pop->size);
778   printf("Crossover %f Mutation %f Migration %f\n", pop->crossover_ratio, pop->mutation_ratio, pop->migration_ratio);
779   printf("Allele mutation prob %f\n", pop->allele_mutation_prob);
780   printf("Allele ranges %d - %d %f - %f\n", pop->allele_min_integer, pop->allele_max_integer, pop->allele_min_double, pop->allele_max_double);
781   printf("Chromosome length %d count %d\n", pop->len_chromosomes, pop->num_chromosomes);
782   printf("Best fitness %f\n", pop->entity_iarray[0]->fitness);
783 
784   return;
785   }
786 
787 
788 /**********************************************************************
789   ga_entity_dump()
790   synopsis:	Dump some statistics about a entity.
791   parameters:	entity	*john
792   return:	none
793   last updated:	24 Dec 2002
794  **********************************************************************/
795 
ga_entity_dump(population * pop,entity * john)796 void ga_entity_dump(population *pop, entity *john)
797   {
798   printf( "Entity id %d rank %d\n",
799           ga_get_entity_id(pop, john),
800           ga_get_entity_rank(pop, john) );
801   printf( "Fitness %f\n", john->fitness );
802   printf( "data <%s> data0 <%s> chromo <%s> chromo0 <%s>\n",
803           john->data?"defined":"undefined",
804           john->data!=NULL&&((SLList *)john->data)->data!=NULL?"defined":"undefined",
805           john->chromosome?"defined":"undefined",
806           john->chromosome!=NULL&&john->chromosome[0]!=NULL?"defined":"undefined" );
807 
808   return;
809   }
810 
811 
812