aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDimitri Sokolyuk <demon@dim13.org>2012-11-20 01:45:28 +0000
committerDimitri Sokolyuk <demon@dim13.org>2012-11-20 01:45:28 +0000
commit2e34725e723cea5ab3907e45fb4c1f235c466132 (patch)
tree158669a300e450fcec7271b7bf65aa2bfeba73da
parent00c8817cc246a48c567715d7e5921814ee6c150e (diff)
pthreads cleanup
-rw-r--r--weasel.c142
1 files changed, 55 insertions, 87 deletions
diff --git a/weasel.c b/weasel.c
index c71531d..b29d7c7 100644
--- a/weasel.c
+++ b/weasel.c
@@ -28,10 +28,12 @@
#include <unistd.h>
pthread_mutex_t mutexsum;
-pthread_attr_t attr;
+pthread_mutex_t gen;
int population = 1000;
int mutationrate = 100; /* 1/n */
+int dieflag = 0;
+int ngeneration = 0;
float average;
#if 0
@@ -75,7 +77,7 @@ ncpu(void)
static inline char
rndchar()
{
- return alphabet[random() % alphalen];
+ return alphabet[arc4random() % alphalen];
}
float
@@ -145,7 +147,8 @@ printpopulation(Creature *best)
}
printw("\n");
- printcreature(best);
+ if (best)
+ printcreature(best);
clrtobot();
refresh();
}
@@ -153,15 +156,11 @@ printpopulation(Creature *best)
Creature *
pickrandom()
{
- int hasone = 0;
+ do
+ cp = generation[arc4random() % population];
+ while (cp->locked);
- while (!hasone) {
- cp = generation[random() % population];
- if (!cp->locked) {
- cp->locked = 1;
- hasone = 1;
- }
- }
+ cp->locked = 1;
return cp;
}
@@ -186,30 +185,36 @@ intercourse()
Creature *c[3];
int i;
- pthread_mutex_lock(&mutexsum);
- for (i = 0; i < 3; i++) {
- c[i] = pickrandom(population);
- assert(c[i]);
- }
- qsort(c, 3, sizeof(Creature *), cmp);
+ while (!dieflag) {
+ pthread_mutex_lock(&mutexsum);
+ for (i = 0; i < 3; i++)
+ c[i] = pickrandom(population);
+ pthread_mutex_unlock(&mutexsum);
- for (i = 0; i < c[2]->length; i++) {
- if (random() % mutationrate)
- c[2]->genom[i] = c[random() % 2]->genom[i];
- else
- c[2]->genom[i] = rndchar();
- }
- c[2]->genom[i] = '\0';
- c[2]->fitness = calculatefitness(c[2]->genom, c[2]->length);
+ qsort(c, 3, sizeof(Creature *), cmp);
- /* recalculate fitness of parents */
- c[0]->fitness = calculatefitness(c[0]->genom, c[0]->length);
- c[1]->fitness = calculatefitness(c[1]->genom, c[1]->length);
+ for (i = 0; i < c[2]->length; i++) {
+ if (arc4random() % mutationrate)
+ c[2]->genom[i] = c[arc4random() % 2]->genom[i];
+ else
+ c[2]->genom[i] = rndchar();
+ }
+ c[2]->genom[i] = '\0';
+ c[2]->fitness = calculatefitness(c[2]->genom, c[2]->length);
- c[0]->locked = 0;
- c[1]->locked = 0;
- c[2]->locked = 0;
- pthread_mutex_unlock(&mutexsum);
+ /* recalculate fitness of parents */
+ c[0]->fitness = calculatefitness(c[0]->genom, c[0]->length);
+ c[1]->fitness = calculatefitness(c[1]->genom, c[1]->length);
+
+ c[0]->locked = 0;
+ c[1]->locked = 0;
+ c[2]->locked = 0;
+
+ pthread_mutex_lock(&gen);
+ ++ngeneration;
+ pthread_mutex_unlock(&gen);
+
+ }
pthread_exit(NULL);
}
@@ -248,35 +253,13 @@ usage(void)
exit(1);
}
-void
-switchcase(char *s, int *uflag)
-{
- size_t len;
- int (*f)(int);
-
- if (*uflag) {
- f = tolower;
- *uflag = 0;
- } else {
- f = toupper;
- *uflag = 1;
- }
-
- for (len = strlen(s); len--; s++)
- *s = f(*s);
-}
-
int
main(int argc, char **argv)
{
Creature *best;
pthread_t *threads;
- int i, c, n, nthreads;
+ int i = 0, c, n, nthreads;
int display = 1;
- int dontstop = 0;
- int uflag = 1;
- float threshold = 0.90;
- int dieflag = 0;
alphabet = defalpha;
nthreads = ncpu();
@@ -301,13 +284,6 @@ main(int argc, char **argv)
usage();
population = i;
break;
- case 's':
- dontstop = 1;
- break;
- case 'S':
- dontstop = 1;
- threshold = atof(optarg);
- break;
case 't':
i = atoi(optarg);
if (i <= 0)
@@ -324,39 +300,31 @@ main(int argc, char **argv)
aim = argc ? strdup(*argv) : defaim;
alphalen = strlen(alphabet);
- threads = calloc(nthreads, sizeof(pthread_t));
- assert(threads);
initscr();
- srandom(time(NULL));
initpopulation(strlen(aim));
pthread_mutex_init(&mutexsum, NULL);
- pthread_attr_init(&attr);
- // pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
-
- for (i = 0; !dieflag || dontstop; i++) {
- dieflag = success(&best);
- if (dontstop && average > threshold)
- switchcase(aim, &uflag);
- for (n = 0; n < nthreads; n++)
- pthread_create(&threads[n], &attr, intercourse, NULL);
- for (n = 0; n < nthreads; n++)
- pthread_join(threads[n], NULL);
- if (display)
- printpopulation(best);
+ threads = calloc(nthreads, sizeof(pthread_t));
+ assert(threads);
+
+ for (n = 0; n < nthreads; n++) {
+ pthread_create(&threads[n], NULL, intercourse, NULL);
+ pthread_detach(threads[n]);
}
- pthread_attr_destroy(&attr);
- pthread_mutex_destroy(&mutexsum);
+ best = NULL;
+ do
+ if (display)
+ printpopulation(best);
+ while (!(dieflag = success(&best)));
- if (display) {
- printpopulation(best);
- printw("\nhalted after %d generations with population of %d\n",
- nthreads * i / population, population);
- refresh();
- }
endwin();
- return 0;
+ fprintf(stderr, "halted after %d generations with population of %d\n",
+ ngeneration, population);
+
+ pthread_mutex_destroy(&mutexsum);
+
+ pthread_exit(NULL);
}