[Avida-cvs] [avida-svn] r782 - in development: Avida.xcodeproj source/actions source/analyze source/main source/platform/win32-pthread
brysonda@myxo.css.msu.edu
brysonda at myxo.css.msu.edu
Tue Jun 27 19:07:36 PDT 2006
Author: brysonda
Date: 2006-06-27 22:07:36 -0400 (Tue, 27 Jun 2006)
New Revision: 782
Added:
development/source/main/cMutationalNeighborhood.cc
development/source/main/cMutationalNeighborhood.h
development/source/main/cMutationalNeighborhoodResults.h
Modified:
development/Avida.xcodeproj/project.pbxproj
development/source/actions/LandscapeActions.cc
development/source/analyze/cAnalyzeJobQueue.cc
development/source/analyze/cAnalyzeJobQueue.h
development/source/main/cLandscape.cc
development/source/main/cLandscape.h
development/source/platform/win32-pthread/pthread.h
Log:
Lay the basic foundation for Mutational Neighborhood calculation. At the moment this is basically a per-site parallelized single-step full landscape.
Modified: development/Avida.xcodeproj/project.pbxproj
===================================================================
--- development/Avida.xcodeproj/project.pbxproj 2006-06-27 21:15:14 UTC (rev 781)
+++ development/Avida.xcodeproj/project.pbxproj 2006-06-28 02:07:36 UTC (rev 782)
@@ -191,6 +191,7 @@
70C054F80A4F704D002703C1 /* PopulationActions.cc in Sources */ = {isa = PBXBuildFile; fileRef = 70C054C90A4F6E19002703C1 /* PopulationActions.cc */; };
70C054F90A4F704E002703C1 /* SaveLoadActions.cc in Sources */ = {isa = PBXBuildFile; fileRef = 708051A80A1F65FE00CBB8B6 /* SaveLoadActions.cc */; };
70C054FA0A4F7053002703C1 /* PopulationActions.cc in Sources */ = {isa = PBXBuildFile; fileRef = 70C054C90A4F6E19002703C1 /* PopulationActions.cc */; };
+ 70C0557D0A50C587002703C1 /* cMutationalNeighborhood.cc in Sources */ = {isa = PBXBuildFile; fileRef = 70C0557A0A50C57E002703C1 /* cMutationalNeighborhood.cc */; };
70C1EF4808C393BA00F50912 /* cCodeLabel.cc in Sources */ = {isa = PBXBuildFile; fileRef = 70C1EF4608C393BA00F50912 /* cCodeLabel.cc */; };
70C1EF4A08C393BA00F50912 /* cCodeLabel.cc in Sources */ = {isa = PBXBuildFile; fileRef = 70C1EF4608C393BA00F50912 /* cCodeLabel.cc */; };
70C1EF5908C3948C00F50912 /* cCPUMemory.cc in Sources */ = {isa = PBXBuildFile; fileRef = 70C1EF5808C3948C00F50912 /* cCPUMemory.cc */; };
@@ -447,7 +448,7 @@
700E12610A097A0800B604CD /* CMakeLists.txt */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = text; path = CMakeLists.txt; sourceTree = "<group>"; };
700E12630A097A1700B604CD /* CMakeLists.txt */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = text; path = CMakeLists.txt; sourceTree = "<group>"; };
700E28CF0859FFD700CF158A /* tObjectFactory.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tObjectFactory.h; sourceTree = "<group>"; };
- 700E2B83085DE50C00CF158A /* avida-viewer */ = {isa = PBXFileReference; includeInIndex = 0; lastKnownFileType = "compiled.mach-o.executable"; path = "avida-viewer"; sourceTree = BUILT_PRODUCTS_DIR; };
+ 700E2B83085DE50C00CF158A /* avida-viewer */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = "avida-viewer"; sourceTree = BUILT_PRODUCTS_DIR; };
7013845F09028B3E0087ED2E /* cAvidaConfig.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = cAvidaConfig.h; sourceTree = "<group>"; };
7013846009028B3E0087ED2E /* cAvidaConfig.cc */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = cAvidaConfig.cc; sourceTree = "<group>"; };
701384A10902A16F0087ED2E /* defs.h */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.h; path = defs.h; sourceTree = "<group>"; };
@@ -747,6 +748,9 @@
70C054F50A4F701B002703C1 /* SConscript */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = text; path = SConscript; sourceTree = "<group>"; };
70C054F60A4F7030002703C1 /* SConscript */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = text; path = SConscript; sourceTree = "<group>"; };
70C054F70A4F703D002703C1 /* SConscript */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = text; path = SConscript; sourceTree = "<group>"; };
+ 70C0557A0A50C57E002703C1 /* cMutationalNeighborhood.cc */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; path = cMutationalNeighborhood.cc; sourceTree = "<group>"; };
+ 70C0557B0A50C57E002703C1 /* cMutationalNeighborhood.h */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.h; path = cMutationalNeighborhood.h; sourceTree = "<group>"; };
+ 70C0557C0A50C57E002703C1 /* cMutationalNeighborhoodResults.h */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.h; path = cMutationalNeighborhoodResults.h; sourceTree = "<group>"; };
70C1EF4608C393BA00F50912 /* cCodeLabel.cc */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; path = cCodeLabel.cc; sourceTree = "<group>"; };
70C1EF4708C393BA00F50912 /* cCodeLabel.h */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.h; path = cCodeLabel.h; sourceTree = "<group>"; };
70C1EF5808C3948C00F50912 /* cCPUMemory.cc */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; path = cCPUMemory.cc; sourceTree = "<group>"; };
@@ -1375,6 +1379,9 @@
DCC310040762539D008F7A48 /* main */ = {
isa = PBXGroup;
children = (
+ 70C0557A0A50C57E002703C1 /* cMutationalNeighborhood.cc */,
+ 70C0557B0A50C57E002703C1 /* cMutationalNeighborhood.h */,
+ 70C0557C0A50C57E002703C1 /* cMutationalNeighborhoodResults.h */,
703CA36F0A5072B700AB4DB4 /* SConscript */,
DCC3109C0762539E008F7A48 /* avida.cc */,
70B086BE08F5D86100FC65FE /* avida.h */,
@@ -2219,6 +2226,7 @@
708051B20A1F663100CBB8B6 /* SaveLoadActions.cc in Sources */,
708051BB0A1F66B400CBB8B6 /* cActionLibrary.cc in Sources */,
70C054ED0A4F6FD2002703C1 /* PopulationActions.cc in Sources */,
+ 70C0557D0A50C587002703C1 /* cMutationalNeighborhood.cc in Sources */,
);
runOnlyForDeploymentPostprocessing = 0;
};
Modified: development/source/actions/LandscapeActions.cc
===================================================================
--- development/source/actions/LandscapeActions.cc 2006-06-27 21:15:14 UTC (rev 781)
+++ development/source/actions/LandscapeActions.cc 2006-06-28 02:07:36 UTC (rev 782)
@@ -19,6 +19,8 @@
#include "cGenotypeBatch.h"
#include "cHardwareManager.h"
#include "cLandscape.h"
+#include "cMutationalNeighborhood.h"
+#include "cMutationalNeighborhoodResults.h"
#include "cStats.h"
#include "cString.h"
#include "cWorld.h"
@@ -214,7 +216,7 @@
tListIterator<cAnalyzeGenotype> batch_it(m_world->GetAnalyze().GetCurrentBatch().List());
cAnalyzeGenotype* genotype = NULL;
while (genotype = batch_it.Next()) {
- cLandscape* land = new cLandscape(m_world, genotype->GetGenome(), inst_set);
+ land = new cLandscape(m_world, genotype->GetGenome(), inst_set);
land->SetDistance(m_dist);
m_batch.PushRear(land);
jobqueue.AddJob(new tAnalyzeJob<cLandscape>(land, &cLandscape::Process));
@@ -382,6 +384,73 @@
};
+class cActionMutationalNeighborhood : public cAction
+{
+private:
+ cString m_filename;
+ tList<cMutationalNeighborhood> m_batch;
+
+public:
+ cActionMutationalNeighborhood(cWorld* world, const cString& args)
+ : cAction(world, args), m_filename("mut-neighborhood.dat")
+ {
+ cString largs(args);
+ if (largs.GetSize()) m_filename = largs.PopWord();
+ }
+
+ const cString GetDescription()
+ {
+ return "MutationalNeighborhood [filename='mut-neighborhood.dat']";
+ }
+
+ void Process(cAvidaContext& ctx)
+ {
+ int update = -1;
+ cMutationalNeighborhood* mutn = NULL;
+ cInstSet& inst_set = m_world->GetHardwareManager().GetInstSet();
+
+ if (ctx.GetAnalyzeMode()) {
+ if (m_world->GetConfig().VERBOSITY.Get() >= VERBOSE_ON) {
+ cString msg("Calculating Mutational Neighborhood for batch ");
+ msg += cStringUtil::Convert(m_world->GetAnalyze().GetCurrentBatchID());
+ m_world->GetDriver().NotifyComment(msg);
+ } else if (m_world->GetConfig().VERBOSITY.Get() > VERBOSE_SILENT) {
+ m_world->GetDriver().NotifyComment("Calculating Mutational Neighborhood...");
+ }
+
+ cAnalyzeJobQueue& jobqueue = m_world->GetAnalyze().GetJobQueue();
+ tListIterator<cAnalyzeGenotype> batch_it(m_world->GetAnalyze().GetCurrentBatch().List());
+ cAnalyzeGenotype* genotype = NULL;
+ while (genotype = batch_it.Next()) {
+ mutn = new cMutationalNeighborhood(m_world, genotype->GetGenome(), inst_set);
+ m_batch.PushRear(mutn);
+ jobqueue.AddJob(new tAnalyzeJob<cMutationalNeighborhood>(mutn, &cMutationalNeighborhood::Process));
+ }
+ jobqueue.Execute();
+ } else {
+ if (m_world->GetConfig().VERBOSITY.Get() >= VERBOSE_DETAILS)
+ m_world->GetDriver().NotifyComment("Full Landscaping...");
+
+ const cGenome& best_genome = m_world->GetClassificationManager().GetBestGenotype()->GetGenome();
+ mutn = new cMutationalNeighborhood(m_world, best_genome, inst_set);
+
+ m_batch.PushRear(mutn);
+ mutn->Process(ctx);
+ update = m_world->GetStats().GetUpdate();
+ }
+
+ cMutationalNeighborhoodResults* results = NULL;
+ cDataFile& df = m_world->GetDataFile(m_filename);
+ while (mutn = m_batch.Pop()) {
+ results = new cMutationalNeighborhoodResults(mutn);
+ results->PrintStats(df, update);
+ delete results;
+ delete mutn;
+ }
+ }
+};
+
+
void RegisterLandscapeActions(cActionLibrary* action_lib)
{
action_lib->Register<cActionAnalyzeLandscape>("AnalyzeLandscape");
@@ -389,4 +458,5 @@
action_lib->Register<cActionFullLandscape>("FullLandscape");
action_lib->Register<cActionRandomLandscape>("RandomLandscape");
action_lib->Register<cActionSampleLandscape>("SampleLandscape");
+ action_lib->Register<cActionMutationalNeighborhood>("MutationalNeighborhood");
}
Modified: development/source/analyze/cAnalyzeJobQueue.cc
===================================================================
--- development/source/analyze/cAnalyzeJobQueue.cc 2006-06-27 21:15:14 UTC (rev 781)
+++ development/source/analyze/cAnalyzeJobQueue.cc 2006-06-28 02:07:36 UTC (rev 782)
@@ -81,6 +81,15 @@
}
+void cAnalyzeJobQueue::Start()
+{
+ if (m_world->GetConfig().VERBOSITY.Get() >= VERBOSE_DETAILS)
+ m_world->GetDriver().NotifyComment("waking worker threads...");
+
+ pthread_cond_broadcast(&m_cond);
+}
+
+
void cAnalyzeJobQueue::Execute()
{
if (m_world->GetConfig().VERBOSITY.Get() >= VERBOSE_DETAILS)
Modified: development/source/analyze/cAnalyzeJobQueue.h
===================================================================
--- development/source/analyze/cAnalyzeJobQueue.h 2006-06-27 21:15:14 UTC (rev 781)
+++ development/source/analyze/cAnalyzeJobQueue.h 2006-06-28 02:07:36 UTC (rev 782)
@@ -63,6 +63,7 @@
void AddJob(cAnalyzeJob* job);
void AddJobImmediate(cAnalyzeJob* job);
+ void Start();
void Execute();
cRandom* GetRandom(int jobid) { return m_rng_pool[jobid & MT_RANDOM_INDEX_MASK]; }
Modified: development/source/main/cLandscape.cc
===================================================================
--- development/source/main/cLandscape.cc 2006-06-27 21:15:14 UTC (rev 781)
+++ development/source/main/cLandscape.cc 2006-06-28 02:07:36 UTC (rev 782)
@@ -48,8 +48,6 @@
total_fitness = 0.0;
total_sqr_fitness = 0.0;
distance = 0;
- del_distance = 0;
- ins_distance = 0;
trials = 0;
total_count = 0;
@@ -87,7 +85,7 @@
{
testcpu->TestGenome(ctx, test_info, in_genome);
- test_fitness = test_info.GetColonyFitness();
+ double test_fitness = test_info.GetColonyFitness();
total_fitness += test_fitness;
total_sqr_fitness += test_fitness * test_fitness;
Modified: development/source/main/cLandscape.h
===================================================================
--- development/source/main/cLandscape.h 2006-06-27 21:15:14 UTC (rev 781)
+++ development/source/main/cLandscape.h 2006-06-28 02:07:36 UTC (rev 782)
@@ -46,8 +46,6 @@
double total_sqr_fitness;
int distance;
- int del_distance;
- int ins_distance;
int trials;
int m_min_found;
@@ -73,9 +71,6 @@
double neg_epi_size;
double no_epi_size;
-
- double test_fitness;
-
int * site_count;
double total_entropy;
Added: development/source/main/cMutationalNeighborhood.cc
===================================================================
--- development/source/main/cMutationalNeighborhood.cc 2006-06-27 21:15:14 UTC (rev 781)
+++ development/source/main/cMutationalNeighborhood.cc 2006-06-28 02:07:36 UTC (rev 782)
@@ -0,0 +1,302 @@
+/*
+ * cMutationalNeighborhood.cc
+ * Avida
+ *
+ * Created by David on 6/13/06.
+ * Copyright 2006 Michigan State University. All rights reserved.
+ *
+ */
+
+#include "cMutationalNeighborhood.h"
+
+#include "cAnalyze.h"
+#include "cAnalyzeJobQueue.h"
+#include "cCPUTestInfo.h"
+#include "cCPUMemory.h"
+#include "cEnvironment.h"
+#include "cInstSet.h"
+#include "cHardwareManager.h"
+#include "cOrganism.h"
+#include "cPhenotype.h"
+#include "cStats.h" // For GetUpdate in outputs...
+#include "cTestCPU.h"
+#include "cTestUtil.h"
+#include "cTools.h"
+#include "cWorld.h"
+#include "tAnalyzeJob.h"
+
+using namespace std;
+
+
+void cMutationalNeighborhood::Process(cAvidaContext& ctx)
+{
+ pthread_mutex_lock(&m_mutex);
+ if (m_initialized) {
+ int cur_site = m_cur_site++;
+ pthread_mutex_unlock(&m_mutex);
+
+ if (cur_site < m_base_genome.GetSize()) {
+ // Create test infrastructure
+ cTestCPU* testcpu = m_world->GetHardwareManager().CreateTestCPU();
+ cCPUTestInfo test_info;
+
+ // Setup One Step Data
+ sOneStep& odata = m_onestep[cur_site];
+ odata.peak_fitness = m_base_fitness;
+ odata.peak_genome = m_base_genome;
+ odata.fitness.Resize(m_inst_set.GetSize(), 0.0);
+ odata.site_count.Resize(m_base_genome.GetSize(), 0);
+
+ // Setup Data Used in Two Step
+ sTwoStep& tdata = m_twostep[cur_site];
+ tdata.peak_fitness = m_base_fitness;
+ tdata.peak_genome = m_base_genome;
+ tdata.site_count.Resize(m_base_genome.GetSize(), 0);
+
+ // Do the processing, starting with One Step
+ ProcessOneStep(ctx, testcpu, test_info, cur_site);
+
+ // Cleanup
+ delete testcpu;
+ }
+ } else {
+ ProcessInitialize(ctx);
+ return;
+ }
+
+ pthread_mutex_lock(&m_mutex);
+ if (++m_completed == m_base_genome.GetSize()) ProcessComplete(ctx);
+ pthread_mutex_unlock(&m_mutex);
+}
+
+
+void cMutationalNeighborhood::ProcessInitialize(cAvidaContext& ctx)
+{
+ // Generate base information
+ cTestCPU* testcpu = m_world->GetHardwareManager().CreateTestCPU();
+ cCPUTestInfo test_info;
+ testcpu->TestGenome(ctx, test_info, m_base_genome);
+
+ cPhenotype& phenotype = test_info.GetColonyOrganism()->GetPhenotype();
+ m_base_fitness = test_info.GetColonyFitness();
+ m_base_merit = phenotype.GetMerit().GetDouble();
+ m_base_gestation = phenotype.GetGestationTime();
+ m_base_tasks = phenotype.GetLastTaskCount();
+
+ m_neut_min = m_base_fitness * nHardware::FITNESS_NEUTRAL_MIN;
+ m_neut_max = m_base_fitness * nHardware::FITNESS_NEUTRAL_MAX;
+
+ delete testcpu;
+
+ // Setup state to begin processing
+ m_onestep.ResizeClear(m_base_genome.GetSize());
+ m_twostep.ResizeClear(m_base_genome.GetSize());
+
+ m_cur_site = 0;
+ m_completed = 0;
+ m_initialized = true;
+
+ // Unlock internal mutex (was locked on Process() entrance)
+ // - will allow workers to begin processing if job queue already active
+ pthread_mutex_unlock(&m_mutex);
+
+ // Load enough jobs to process all sites
+ cAnalyzeJobQueue& jobqueue = m_world->GetAnalyze().GetJobQueue();
+ for (int i = 0; i < m_base_genome.GetSize(); i++)
+ jobqueue.AddJob(new tAnalyzeJob<cMutationalNeighborhood>(this, &cMutationalNeighborhood::Process));
+
+ jobqueue.Start();
+}
+
+
+void cMutationalNeighborhood::ProcessOneStep(cAvidaContext& ctx, cTestCPU* testcpu, cCPUTestInfo& test_info, int cur_site)
+{
+ const int inst_size = m_inst_set.GetSize();
+ sOneStep& odata = m_onestep[cur_site];
+
+ cGenome mod_genome(m_base_genome);
+
+ // Loop through all the lines of genome, testing trying all combinations.
+ int cur_inst = mod_genome[cur_site].GetOp();
+
+ // Loop through all instructions...
+ for (int inst_num = 0; inst_num < inst_size; inst_num++) {
+ if (cur_inst == inst_num) continue;
+
+ mod_genome[cur_site].SetOp(inst_num);
+ testcpu->TestGenome(ctx, test_info, mod_genome);
+
+ double test_fitness = test_info.GetColonyFitness();
+
+ odata.total_fitness += test_fitness;
+ odata.total_sqr_fitness += test_fitness * test_fitness;
+ odata.total++;
+ if (test_fitness == 0.0) {
+ odata.dead++;
+ } else if (test_fitness < m_neut_min) {
+ odata.neg++;
+ odata.size_neg += test_fitness;
+ } else if (test_fitness <= m_neut_max) {
+ odata.neut++;
+ } else {
+ odata.pos++;
+ odata.size_pos += test_fitness;
+ if (test_fitness > odata.peak_fitness) {
+ odata.peak_fitness = test_fitness;
+ odata.peak_genome = mod_genome;
+ }
+ }
+
+ if (test_fitness >= m_neut_min) odata.site_count[cur_site]++;
+
+ odata.fitness[cur_inst] = test_fitness;
+ odata.cur_tasks = test_info.GetColonyOrganism()->GetPhenotype().GetLastTaskCount();
+
+ // @TODO - calculate task values
+
+ //ProcessTwoStep(ctx, testcpu, test_info, cur_site, mod_genome);
+ }
+}
+
+void cMutationalNeighborhood::ProcessTwoStep(cAvidaContext& ctx, cTestCPU* testcpu, cCPUTestInfo& test_info, int cur_site, cGenome& mod_genome)
+{
+ const int inst_size = m_inst_set.GetSize();
+ sOneStep& odata = m_onestep[cur_site];
+ sTwoStep& tdata = m_twostep[cur_site];
+
+ // Loop through remaining lines of genome, testing trying all combinations.
+ for (int line_num = cur_site + 1; line_num < m_base_genome.GetSize(); line_num++) {
+ int cur_inst = mod_genome[line_num].GetOp();
+
+ // Loop through all instructions...
+ for (int inst_num = 0; inst_num < inst_size; inst_num++) {
+ if (cur_inst == inst_num) continue;
+
+ mod_genome[line_num].SetOp(inst_num);
+ testcpu->TestGenome(ctx, test_info, mod_genome);
+
+ double test_fitness = test_info.GetColonyFitness();
+
+ tdata.total_fitness += test_fitness;
+ tdata.total_sqr_fitness += test_fitness * test_fitness;
+ tdata.total++;
+ if (test_fitness == 0.0) {
+ tdata.dead++;
+ } else if (test_fitness < m_neut_min) {
+ tdata.neg++;
+ tdata.size_neg += test_fitness;
+ } else if (test_fitness <= m_neut_max) {
+ tdata.neut++;
+ } else {
+ tdata.pos++;
+ tdata.size_pos += test_fitness;
+ if (test_fitness > tdata.peak_fitness) {
+ tdata.peak_fitness = test_fitness;
+ tdata.peak_genome = mod_genome;
+ }
+ }
+
+ if (test_fitness >= m_neut_min) tdata.site_count[line_num]++;
+
+ // @TODO - calculate task values
+ }
+
+ mod_genome[line_num].SetOp(cur_inst);
+ }
+}
+
+
+void cMutationalNeighborhood::ProcessComplete(cAvidaContext& ctx)
+{
+ // Initialize values
+ m_total = 0;
+ m_total_sqr_fitness = 0.0;
+ m_dead = 0;
+ m_neg = 0;
+ m_neut = 0;
+ m_pos = 0;
+ m_size_pos = 0.0;
+ m_size_neg = 0.0;
+ m_peak_fitness = m_base_fitness;
+ m_peak_genome = m_base_genome;
+ m_site_count.Resize(m_base_genome.GetSize(), 0);
+
+ for (int i = 0; i < m_onestep.GetSize(); i++) {
+ sOneStep& odata = m_onestep[i];
+ m_total += odata.total;
+ m_total_fitness += odata.total_fitness;
+ m_total_sqr_fitness += odata.total_sqr_fitness;
+ m_dead += odata.dead;
+ m_neg += odata.neg;
+ m_neut += odata.neut;
+ m_pos += odata.pos;
+ m_size_pos += odata.size_pos;
+ m_size_neg += odata.size_neg;
+
+ if (odata.peak_fitness > m_peak_fitness) {
+ m_peak_genome = odata.peak_genome;
+ m_peak_fitness = odata.peak_fitness;
+ }
+
+
+ for (int j = 0; j < m_site_count.GetSize(); j++) {
+ m_site_count[j] += odata.site_count[j];
+ }
+
+ // @TODO - aggregate task data
+ }
+
+ double max_ent = log(static_cast<double>(m_inst_set.GetSize()));
+ m_total_entropy = 0;
+ for (int i = 0; i < m_base_genome.GetSize(); i++) {
+ // Per-site entropy is the log of the number of legal states for that
+ // site. Add one to account for the unmutated state.
+ m_total_entropy += log(static_cast<double>(m_site_count[i] + 1)) / max_ent;
+ }
+ m_complexity = m_base_genome.GetSize() - m_total_entropy;
+
+
+ // @TODO - aggregate two step task data
+
+
+ pthread_rwlock_unlock(&m_rwlock);
+}
+
+
+void cMutationalNeighborhood::PrintStats(cDataFile& df, int update)
+{
+ df.Write(update, "Update");
+ df.Write(m_base_fitness, "Base Fitness");
+ df.Write(m_base_merit, "Base Merit");
+ df.Write(m_base_gestation, "Base Gestation");
+ df.Write(m_total, "Total One Step Mutants");
+ df.Write(GetProbDead(), "One Step Probability Dead");
+ df.Write(GetProbNeg(), "One Step Probability Deleterious");
+ df.Write(GetProbNeut(), "One Step Probability Neutral");
+ df.Write(GetProbPos(), "One Step Probability Positive");
+ df.Write(GetAvPosSize(), "One Step Average Positive Size");
+ df.Write(GetAvNegSize(), "One Step Average Negative Size");
+ df.Write(m_peak_fitness, "One Step Peak Fitness");
+ df.Write(GetAveFitness(), "One Step Average Fitness");
+ df.Write(GetAveSqrFitness(), "One Step Average Square Fitness");
+ df.Write(m_total_entropy, "One Step Total Entropy");
+ df.Write(m_complexity, "One Step Total Complexity");
+ df.Endl();
+}
+
+void cMutationalNeighborhood::PrintEntropy(cDataFile& df)
+{
+ double max_ent = log(static_cast<double>(m_inst_set.GetSize()));
+ for (int j = 0; j < m_base_genome.GetSize(); j++) {
+ df.Write(log(static_cast<double>(m_site_count[j] + 1)) / max_ent, " ");
+ }
+ df.Endl();
+}
+
+void cMutationalNeighborhood::PrintSiteCount(cDataFile& df)
+{
+ for (int j = 0; j < m_base_genome.GetSize(); j++) {
+ df.Write(m_site_count[j], " ");
+ }
+ df.Endl();
+}
Added: development/source/main/cMutationalNeighborhood.h
===================================================================
--- development/source/main/cMutationalNeighborhood.h 2006-06-27 21:15:14 UTC (rev 781)
+++ development/source/main/cMutationalNeighborhood.h 2006-06-28 02:07:36 UTC (rev 782)
@@ -0,0 +1,250 @@
+/*
+ * cMutationalNeighborhood.h
+ * Avida
+ *
+ * Created by David on 6/13/06.
+ * Copyright 2006 Michigan State University. All rights reserved.
+ *
+ */
+
+#ifndef cMutationalNeighborhood_h
+#define cMutationalNeighborhood_h
+
+#ifndef cGenome_h
+#include "cGenome.h"
+#endif
+#ifndef cString_h
+#include "cString.h"
+#endif
+#ifndef tArray_h
+#include "tArray.h"
+#endif
+
+#include <pthread.h>
+
+class cAvidaContext;
+class cCPUTestInfo;
+class cDataFile;
+class cInstSet;
+class cInstruction;
+class cTestCPU;
+class cWorld;
+
+
+class cMutationalNeighborhood
+{
+ friend class cMutationalNeighborhoodResults;
+
+private:
+ cWorld* m_world;
+
+ // Internal state information
+ // --------------------------------------------------------------------------
+ pthread_rwlock_t m_rwlock;
+ pthread_mutex_t m_mutex;
+
+ bool m_initialized;
+ int m_cur_site;
+ int m_completed;
+
+ struct sOneStep
+ {
+ int total;
+
+ double total_fitness;
+ double total_sqr_fitness;
+ cGenome peak_genome;
+ double peak_fitness;
+
+ int dead;
+ int neg;
+ int neut;
+ int pos;
+ double size_pos;
+ double size_neg;
+
+ tArray<int> site_count;
+
+ int task_target;
+ int task_total;
+ int task_knockout;
+
+ // state used in two step calculations
+ tArray<double> fitness;
+ tArray<int> cur_tasks;
+
+ sOneStep() : total(0), total_fitness(0.0), total_sqr_fitness(0.0), peak_fitness(0.0), dead(0), neg(0), neut(0), pos(0),
+ size_pos(0.0), size_neg(0.0), task_target(0), task_total(0), task_knockout(0) { ; }
+ };
+ tArray<sOneStep> m_onestep;
+
+ struct sTwoStep
+ {
+ int total;
+
+ double total_fitness;
+ double total_sqr_fitness;
+ cGenome peak_genome;
+ double peak_fitness;
+
+ int dead;
+ int neg;
+ int neut;
+ int pos;
+ double size_pos;
+ double size_neg;
+
+ tArray<int> site_count;
+
+ int task_target;
+ int task_target_pos;
+ int task_target_neg;
+ int task_target_neut;
+ int task_target_dead;
+ int task_total;
+ int task_knockout;
+
+ sTwoStep() : total(0), total_fitness(0.0), total_sqr_fitness(0.0), peak_fitness(0.0), dead(0), neg(0), neut(0), pos(0),
+ size_pos(0.0), size_neg(0.0), task_target(0), task_target_pos(0), task_target_neg(0), task_target_dead(0),
+ task_total(0), task_knockout(0) { ; }
+ };
+ tArray<sTwoStep> m_twostep;
+
+ const cInstSet& m_inst_set;
+
+ // Base data
+ // --------------------------------------------------------------------------
+ cGenome m_base_genome;
+ double m_base_fitness;
+ double m_base_merit;
+ double m_base_gestation;
+ tArray<int> m_base_tasks;
+ double m_neut_min; // These two variables are a range around the base
+ double m_neut_max; // fitness to be counted as neutral mutations.
+
+ // Aggregated data
+ // --------------------------------------------------------------------------
+ int m_total;
+
+ double m_total_fitness;
+ double m_total_sqr_fitness;
+ cGenome m_peak_genome;
+ double m_peak_fitness;
+
+ int m_dead;
+ int m_neg;
+ int m_neut;
+ int m_pos;
+ double m_size_pos;
+ double m_size_neg;
+
+ tArray<int> m_site_count;
+
+ double m_total_entropy;
+ double m_complexity;
+
+ // Single step task totals
+ int m_stask_target;
+ int m_stask_total;
+ int m_stask_knockout;
+
+ // Two step task totals
+ int m_ttask_target;
+ int m_ttask_target_pos;
+ int m_ttask_target_neg;
+ int m_ttask_target_neut;
+ int m_ttask_target_dead;
+ int m_ttask_total;
+ int m_ttask_knockout;
+
+
+ void ProcessInitialize(cAvidaContext& ctx);
+ void ProcessOneStep(cAvidaContext& ctx, cTestCPU* testcpu, cCPUTestInfo& test_info, int cur_site);
+ void ProcessTwoStep(cAvidaContext& ctx, cTestCPU* testcpu, cCPUTestInfo& test_info, int cur_site, cGenome& mod_genome);
+ void ProcessComplete(cAvidaContext& ctx);
+
+ cMutationalNeighborhood(); // @not_implemented
+ cMutationalNeighborhood(const cMutationalNeighborhood&); // @not_implemented
+ cMutationalNeighborhood& operator=(const cMutationalNeighborhood&); // @not_implemented
+
+public:
+ cMutationalNeighborhood(cWorld* world, const cGenome& genome, const cInstSet& inst_set)
+ : m_world(world), m_initialized(false), m_inst_set(inst_set), m_base_genome(genome)
+ {
+ pthread_rwlock_init(&m_rwlock, NULL);
+ pthread_mutex_init(&m_mutex, NULL);
+
+ // Acquire write lock, to prevent any Results instances before computing
+ pthread_rwlock_wrlock(&m_rwlock);
+ }
+ ~cMutationalNeighborhood()
+ {
+ pthread_rwlock_destroy(&m_rwlock);
+ pthread_mutex_destroy(&m_mutex);
+ }
+
+ void Process(cAvidaContext& ctx);
+
+
+// These methods can only be accessed via a cMutationalNeighborhoodResults object
+private:
+ void PrintStats(cDataFile& df, int update = -1);
+ void PrintEntropy(cDataFile& df);
+ void PrintSiteCount(cDataFile& df);
+
+ inline const cGenome& GetBaseGenome() const { return m_base_genome; }
+ inline double GetBaseFitness() const { return m_base_fitness; }
+
+ inline int GetTotal() const { return m_total; }
+
+ inline double GetAveFitness() const { return m_total_fitness / m_total; }
+ inline double GetAveSqrFitness() const { return m_total_sqr_fitness / m_total; }
+ inline const cGenome& GetPeakGenome() const { return m_peak_genome; }
+ inline double GetPeakFitness() const { return m_peak_fitness; }
+
+ inline double GetProbDead() const { return static_cast<double>(m_dead) / m_total; }
+ inline double GetProbNeg() const { return static_cast<double>(m_neg) / m_total; }
+ inline double GetProbNeut() const { return static_cast<double>(m_neut) / m_total; }
+ inline double GetProbPos() const { return static_cast<double>(m_pos) / m_total; }
+ inline double GetAvPosSize() const { if (m_pos == 0) return 0.0; else return m_size_pos / m_pos; }
+ inline double GetAvNegSize() const { if (m_neg == 0) return 0.0; else return m_size_neg / m_neg; }
+
+ inline double GetTotalEntropy() const { return m_total_entropy; }
+ inline double GetComplexity() const { return m_complexity; }
+
+ inline int GetSingleTargetTask() const { return m_stask_target; }
+ inline double GetProbSingleTargetTask() const { return static_cast<double>(m_stask_target) / m_total; }
+ inline int GetSingleTask() const { return m_stask_total; }
+ inline double GetProbSingleTask() const { return static_cast<double>(m_stask_total) / m_total; }
+ inline int GetSingleKnockout() const { return m_stask_knockout; }
+ inline double GetProbSingleKnockout() const { return static_cast<double>(m_stask_knockout) / m_total; }
+
+ inline int GetDoubleTargetTask() const { return m_ttask_target; }
+ inline double GetProbDoubleTargetTask() const { return static_cast<double>(m_ttask_target) / m_total; }
+ inline int GetDoubleTargetTaskPos() const { return m_ttask_target_pos; }
+ inline double GetProbDoubleTargetTaskPos() const { return static_cast<double>(m_ttask_target_pos) / m_total; }
+ inline int GetDoubleTargetTaskNeg() const { return m_ttask_target_neg; }
+ inline double GetProbDoubleTargetTaskNeg() const { return static_cast<double>(m_ttask_target_neg) / m_total; }
+ inline int GetDoubleTargetTaskNeut() const { return m_ttask_target_neut; }
+ inline double GetProbDoubleTargetTaskNeut() const { return static_cast<double>(m_ttask_target_neut) / m_total; }
+ inline int GetDoubleTargetTaskDead() const { return m_ttask_target_dead; }
+ inline double GetProbDoubleTargetTaskDead() const { return static_cast<double>(m_ttask_target_dead) / m_total; }
+ inline int GetDoubleTask() const { return m_stask_total; }
+ inline double GetProbDoubleTask() const { return static_cast<double>(m_stask_total) / m_total; }
+ inline int GetDoubleKnockout() const { return m_stask_knockout; }
+ inline double GetProbDoubleKnockout() const { return static_cast<double>(m_stask_knockout) / m_total; }
+};
+
+
+#ifdef ENABLE_UNIT_TESTS
+namespace nMutationalNeighborhood {
+ /**
+ * Run unit tests
+ *
+ * @param full Run full test suite; if false, just the fast tests.
+ **/
+ void UnitTests(bool full = false);
+}
+#endif
+
+#endif
Added: development/source/main/cMutationalNeighborhoodResults.h
===================================================================
--- development/source/main/cMutationalNeighborhoodResults.h 2006-06-27 21:15:14 UTC (rev 781)
+++ development/source/main/cMutationalNeighborhoodResults.h 2006-06-28 02:07:36 UTC (rev 782)
@@ -0,0 +1,88 @@
+/*
+ * cMutationalNeighborhoodResults.h
+ * Avida
+ *
+ * Created by David Bryson on 6/21/06.
+ * Copyright 2006 Michigan State University. All rights reserved.
+ *
+ */
+
+#ifndef cMutationalNeighborhoodResults_h
+#define cMutationalNeighborhoodResults_h
+
+#ifndef cMutationalNeighborhood_h
+#include "cMutationalNeighborhood.h"
+#endif
+
+class cMutationalNeighborhoodResults
+{
+private:
+ cMutationalNeighborhood& m_src;
+
+ cMutationalNeighborhoodResults(); // @not_implemented
+ cMutationalNeighborhoodResults(const cMutationalNeighborhood&); // @not_implemented
+ cMutationalNeighborhoodResults& operator=(const cMutationalNeighborhoodResults&); // @not_implemented
+
+public:
+ cMutationalNeighborhoodResults(cMutationalNeighborhood& src) : m_src(src)
+ {
+ pthread_rwlock_rdlock(&m_src.m_rwlock);
+ }
+ cMutationalNeighborhoodResults(cMutationalNeighborhood* src) : m_src(*src)
+ {
+ pthread_rwlock_rdlock(&m_src.m_rwlock);
+ }
+
+ ~cMutationalNeighborhoodResults()
+ {
+ pthread_rwlock_unlock(&m_src.m_rwlock);
+ }
+
+ inline void PrintStats(cDataFile& df, int update = -1) const { m_src.PrintStats(df, update); }
+ inline void PrintEntropy(cDataFile& df) const { m_src.PrintEntropy(df); }
+ inline void PrintSiteCount(cDataFile& df) const { m_src.PrintSiteCount(df); }
+
+ inline const cGenome& GetBaseGenome() const { return m_src.GetBaseGenome(); }
+ inline double GetBaseFitness() const { return m_src.GetBaseFitness(); }
+
+ inline int GetTotal() const { return m_src.GetTotal(); }
+
+ inline double GetAveFitness() const { return m_src.GetAveFitness(); }
+ inline double GetAveSqrFitness() const { return m_src.GetAveSqrFitness(); }
+ inline const cGenome& GetPeakGenome() const { return m_src.GetPeakGenome(); }
+ inline double GetPeakFitness() const { return m_src.GetPeakFitness(); }
+
+ inline double GetProbDead() const { return m_src.GetProbDead(); }
+ inline double GetProbNeg() const { return m_src.GetProbNeg(); }
+ inline double GetProbNeut() const { return m_src.GetProbNeut(); }
+ inline double GetProbPos() const { return m_src.GetProbPos(); }
+ inline double GetAvPosSize() const { return m_src.GetAvPosSize(); }
+ inline double GetAvNegSize() const { return m_src.GetAvNegSize(); }
+
+ inline double GetTotalEntropy() const { return m_src.GetTotalEntropy(); }
+ inline double GetComplexity() const { return m_src.GetComplexity(); }
+
+ inline int GetSingleTargetTask() const { return m_src.GetSingleTargetTask(); }
+ inline double GetProbSingleTargetTask() const { return m_src.GetProbSingleTargetTask(); }
+ inline int GetSingleTask() const { return m_src.GetProbSingleTask(); }
+ inline double GetProbSingleTask() const { return m_src.GetProbSingleTask(); }
+ inline int GetSingleKnockout() const { return m_src.GetSingleKnockout(); }
+ inline double GetProbSingleKnockout() const { return m_src.GetProbSingleKnockout(); }
+
+ inline int GetDoubleTargetTask() const { return m_src.GetDoubleTargetTask(); }
+ inline double GetProbDoubleTargetTask() const { return m_src.GetProbDoubleTargetTask(); }
+ inline int GetDoubleTargetTaskPos() const { return m_src.GetDoubleTargetTaskPos(); }
+ inline double GetProbDoubleTargetTaskPos() const { return m_src.GetProbDoubleTargetTaskPos(); }
+ inline int GetDoubleTargetTaskNeg() const { return m_src.GetDoubleTargetTaskNeg(); }
+ inline double GetProbDoubleTargetTaskNeg() const { return m_src.GetProbDoubleTargetTaskNeg(); }
+ inline int GetDoubleTargetTaskNeut() const { return m_src.GetDoubleTargetTaskNeut(); }
+ inline double GetProbDoubleTargetTaskNeut() const { return m_src.GetProbDoubleTargetTaskNeut(); }
+ inline int GetDoubleTargetTaskDead() const { return m_src.GetDoubleTargetTaskDead(); }
+ inline double GetProbDoubleTargetTaskDead() const { return m_src.GetProbDoubleTargetTaskDead(); }
+ inline int GetDoubleTask() const { return m_src.GetProbDoubleTask(); }
+ inline double GetProbDoubleTask() const { return m_src.GetProbDoubleTask(); }
+ inline int GetDoubleKnockout() const { return m_src.GetDoubleKnockout(); }
+ inline double GetProbDoubleKnockout() const { return m_src.GetProbDoubleKnockout(); }
+};
+
+#endif
Modified: development/source/platform/win32-pthread/pthread.h
===================================================================
--- development/source/platform/win32-pthread/pthread.h 2006-06-27 21:15:14 UTC (rev 781)
+++ development/source/platform/win32-pthread/pthread.h 2006-06-28 02:07:36 UTC (rev 782)
@@ -28,6 +28,14 @@
#define pthread_cond_broadcast(x)
#define pthread_cond_destroy(x)
+// Just define away rwlock support
+#define pthread_rwlock_t int
+#define pthread_rwlock_init(x, y)
+#define pthread_rwlock_rdlock(x)
+#define pthread_rwlock_wrlock(x)
+#define pthread_rwlock_unlock(x)
+#define pthread_rwlock_destroy(x)
+
// Define away pthread support
#define pthread_t int
#define pthread_exit(x)
More information about the Avida-cvs
mailing list