X-Git-Url: https://git.octo.it/?a=blobdiff_plain;ds=sidebyside;f=src%2Flibpopulation.c;h=c27fd9bf7adf0306296605b4f1fa9e8fc27ec365;hb=HEAD;hp=26345f86026fe5e53b5d34593b125b988c39afc9;hpb=9cd71de93b412bd24e5e5b512ec0b774f4123b9d;p=libpopulation.git diff --git a/src/libpopulation.c b/src/libpopulation.c index 26345f8..c27fd9b 100644 --- a/src/libpopulation.c +++ b/src/libpopulation.c @@ -1,6 +1,6 @@ /** - * libevolve - src/evolve.c - * Copyright (C) 2008 Florian octo Forster + * libpopulation - src/evolve.c + * Copyright (C) 2008,2009 Florian octo Forster * * This program is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the @@ -107,6 +107,7 @@ struct population_s #define POPULATION_FLAG_LISTEN 0x01 #define POPULATION_FLAG_SHUTDOWN 0x02 +#define POPULATION_FLAG_EXPLORE 0x10 int flags; pthread_t listen_thread_id; @@ -489,6 +490,27 @@ int population_set_serialization (population_t *p, /* {{{ */ return (0); } /* }}} int population_set_serialization */ +int population_set_replacement_method (population_t *p, int method) /* {{{ */ +{ + int status = 0; + + if (p == NULL) + return (EINVAL); + + pthread_mutex_lock (&p->lock); + + if (method == POPULATION_REPLACEMENT_EXPLOIT) + p->flags &= ~POPULATION_FLAG_EXPLORE; + else if (method == POPULATION_REPLACEMENT_EXPLORE) + p->flags |= POPULATION_FLAG_EXPLORE; + else + status = EINVAL; + + pthread_mutex_unlock (&p->lock); + + return (0); +} /* }}} int population_set_replacement_method */ + int population_add_peer (population_t *p, const char *node, /* {{{ */ const char *port) { @@ -659,7 +681,7 @@ int population_insert (population_t *p, void *pi_orig) /* {{{ */ { void *pi; int pi_rating; - int num_tries; + int sent_to_peer; int i; if (p == NULL) @@ -675,6 +697,25 @@ int population_insert (population_t *p, void *pi_orig) /* {{{ */ return (-1); } + /* + * With a small chance, send this individual to somewhere else. + * `sent_to_peer = -1' is used to signal the following code that this + * individual has been sent to somewhere else and doesn't go into the local + * population. + */ + sent_to_peer = 0; + if (p->peers_num > 0) + { + double prob; + + prob = ((double) rand ()) / (((double) RAND_MAX) + 1.0); + if (prob <= 0.001) + { + population_send_to_peer (p, pi); + sent_to_peer = 1; + } + } + pi_rating = p->rate (pi); pthread_mutex_lock (&p->lock); @@ -694,11 +735,11 @@ int population_insert (population_t *p, void *pi_orig) /* {{{ */ } } - if (p->individuals_num <= 0) + if ((sent_to_peer != 0) || (p->individuals_num <= 0)) { pthread_mutex_unlock (&p->lock); p->free (pi); - return (-1); + return (0); } do @@ -728,6 +769,10 @@ int population_insert (population_t *p, void *pi_orig) /* {{{ */ chance = (int) (((double) (chance_j + chance_pi)) * (rand() / (RAND_MAX + 1.0))); + + if (p->flags & POPULATION_FLAG_EXPLORE) + chance *= .5; + if (chance < chance_j) /* j looses ;) */ { void *temp0; @@ -746,33 +791,7 @@ int population_insert (population_t *p, void *pi_orig) /* {{{ */ pthread_mutex_unlock (&p->lock); if (pi != NULL) - { p->free (pi); - pi = NULL; - } - - while (p->peers_num > 0) - { - double prob; - size_t j; - void *pi; - - prob = ((double) rand ()) / (((double) RAND_MAX) + 1.0); - if (prob < 0.999) - break; - - pi = population_get_random (p); - if (pi == NULL) - { - fprintf (stderr, "population_insert: population_get_random failed.\n"); - break; - } - - population_send_to_peer (p, pi); - p->free (pi); - - break; - } return (0); } /* }}} int population_insert */