[Avida-SVN] r1370 - in branches/dkdev: Avida.xcodeproj source/actions source/cpu source/main
dknoester at myxo.css.msu.edu
dknoester at myxo.css.msu.edu
Sun Feb 25 17:09:53 PST 2007
Author: dknoester
Date: 2007-02-25 20:09:53 -0500 (Sun, 25 Feb 2007)
New Revision: 1370
Modified:
branches/dkdev/Avida.xcodeproj/project.pbxproj
branches/dkdev/source/actions/PopulationActions.cc
branches/dkdev/source/actions/PrintActions.cc
branches/dkdev/source/cpu/cHardwareCPU.cc
branches/dkdev/source/cpu/cHardwareCPU.h
branches/dkdev/source/main/cDeme.cc
branches/dkdev/source/main/cDeme.h
branches/dkdev/source/main/cPopulation.cc
branches/dkdev/source/main/cStats.cc
branches/dkdev/source/main/cStats.h
Log:
Checkpoint commit for topology work. Using ReplicateDemes and checking for completely connected topologies.
Modified: branches/dkdev/Avida.xcodeproj/project.pbxproj
===================================================================
--- branches/dkdev/Avida.xcodeproj/project.pbxproj 2007-02-26 01:09:12 UTC (rev 1369)
+++ branches/dkdev/Avida.xcodeproj/project.pbxproj 2007-02-26 01:09:53 UTC (rev 1370)
@@ -796,7 +796,7 @@
DCC315CF076253A5008F7A48 /* Makefile */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.make; path = Makefile; sourceTree = "<group>"; };
DCC315D0076253A5008F7A48 /* task_event_gen.cc */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; path = task_event_gen.cc; sourceTree = "<group>"; };
DCC315D1076253A5008F7A48 /* task_event_gen.old.cc */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; path = task_event_gen.old.cc; sourceTree = "<group>"; };
- DCC3164D07626CF3008F7A48 /* avida */ = {isa = PBXFileReference; includeInIndex = 0; lastKnownFileType = "compiled.mach-o.executable"; path = avida; sourceTree = BUILT_PRODUCTS_DIR; };
+ DCC3164D07626CF3008F7A48 /* avida */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = avida; sourceTree = BUILT_PRODUCTS_DIR; };
E03F28DA0B8A2840009966B8 /* cDeme.cc */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; path = cDeme.cc; sourceTree = "<group>"; };
E03F28DB0B8A2840009966B8 /* cDeme.h */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.h; path = cDeme.h; sourceTree = "<group>"; };
E08178B90B3DCB9600B474B6 /* cTopology.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = cTopology.h; sourceTree = "<group>"; };
@@ -1944,12 +1944,12 @@
isa = XCBuildConfiguration;
buildSettings = {
GCC_MODEL_CPU = G4;
+ HEADER_SEARCH_PATHS = "/usr/local/include/boost-1_33_1";
OTHER_LDFLAGS = (
"-multiply_defined",
suppress,
);
PRODUCT_NAME = avida;
- USER_HEADER_SEARCH_PATHS = source/main;
};
name = Development;
};
@@ -1957,12 +1957,13 @@
isa = XCBuildConfiguration;
buildSettings = {
GCC_MODEL_CPU = G4;
+ HEADER_SEARCH_PATHS = "/usr/local/include/boost-1_33_1";
OTHER_LDFLAGS = (
"-multiply_defined",
suppress,
);
PRODUCT_NAME = avida;
- USER_HEADER_SEARCH_PATHS = source/main;
+ USER_HEADER_SEARCH_PATHS = "";
};
name = "Deployment-G4";
};
@@ -2077,12 +2078,13 @@
isa = XCBuildConfiguration;
buildSettings = {
GCC_MODEL_CPU = G4;
+ HEADER_SEARCH_PATHS = "/usr/local/include/boost-1_33_1";
OTHER_LDFLAGS = (
"-multiply_defined",
suppress,
);
PRODUCT_NAME = avida;
- USER_HEADER_SEARCH_PATHS = source/main;
+ USER_HEADER_SEARCH_PATHS = "";
};
name = "Deployment-G5";
};
@@ -2090,12 +2092,13 @@
isa = XCBuildConfiguration;
buildSettings = {
GCC_MODEL_CPU = G4;
+ HEADER_SEARCH_PATHS = "/usr/local/include/boost-1_33_1";
OTHER_LDFLAGS = (
"-multiply_defined",
suppress,
);
PRODUCT_NAME = avida;
- USER_HEADER_SEARCH_PATHS = source/main;
+ USER_HEADER_SEARCH_PATHS = "";
};
name = Profile;
};
@@ -2204,12 +2207,13 @@
isa = XCBuildConfiguration;
buildSettings = {
GCC_MODEL_CPU = G4;
+ HEADER_SEARCH_PATHS = "/usr/local/include/boost-1_33_1";
OTHER_LDFLAGS = (
"-multiply_defined",
suppress,
);
PRODUCT_NAME = avida;
- USER_HEADER_SEARCH_PATHS = source/main;
+ USER_HEADER_SEARCH_PATHS = "";
};
name = "Deployment-Universal";
};
Modified: branches/dkdev/source/actions/PopulationActions.cc
===================================================================
--- branches/dkdev/source/actions/PopulationActions.cc 2007-02-26 01:09:12 UTC (rev 1369)
+++ branches/dkdev/source/actions/PopulationActions.cc 2007-02-26 01:09:53 UTC (rev 1370)
@@ -842,6 +842,7 @@
if (in_trigger == "all") m_rep_trigger = 0;
else if (in_trigger == "full_deme") m_rep_trigger = 1;
else if (in_trigger == "corners") m_rep_trigger = 2;
+ else if (in_trigger == "topo-connected") m_rep_trigger = 3;
else {
cString err("Unknown replication trigger '");
err += in_trigger;
Modified: branches/dkdev/source/actions/PrintActions.cc
===================================================================
--- branches/dkdev/source/actions/PrintActions.cc 2007-02-26 01:09:12 UTC (rev 1369)
+++ branches/dkdev/source/actions/PrintActions.cc 2007-02-26 01:09:53 UTC (rev 1370)
@@ -64,6 +64,7 @@
STATS_OUT_FILE(PrintInstructionData, instruction.dat );
STATS_OUT_FILE(PrintGenotypeMap, genotype_map.m );
STATS_OUT_FILE(PrintMarketData, market.dat );
+STATS_OUT_FILE(PrintTopologyData, topology.dat);
#define POP_OUT_FILE(METHOD, DEFAULT) /* 1 */ \
class cAction ## METHOD : public cAction { /* 2 */ \
@@ -1475,6 +1476,7 @@
action_lib->Register<cActionPrintInstructionData>("PrintInstructionData");
action_lib->Register<cActionPrintGenotypeMap>("PrintGenotypeMap");
action_lib->Register<cActionPrintMarketData>("PrintMarketData");
+ action_lib->Register<cActionPrintTopologyData>("PrintTopologyData");
// Population Out Files
action_lib->Register<cActionPrintPhenotypeData>("PrintPhenotypeData");
Modified: branches/dkdev/source/cpu/cHardwareCPU.cc
===================================================================
--- branches/dkdev/source/cpu/cHardwareCPU.cc 2007-02-26 01:09:12 UTC (rev 1369)
+++ branches/dkdev/source/cpu/cHardwareCPU.cc 2007-02-26 01:09:53 UTC (rev 1370)
@@ -31,9 +31,11 @@
#include "cWorld.h"
#include "cPopulation.h"
#include "cPopulationCell.h"
+#include "cDeme.h"
#include <limits.h>
#include <fstream>
+#include <utility>
using namespace std;
@@ -357,7 +359,10 @@
// Messaging instructions
cInstEntryCPU("send-msg", &cHardwareCPU::Inst_SendMessage),
cInstEntryCPU("rtrv-msg", &cHardwareCPU::Inst_RetrieveMessage),
- cInstEntryCPU("cell-id", &cHardwareCPU::Inst_CellID)
+ cInstEntryCPU("cell-id", &cHardwareCPU::Inst_CellID),
+
+ // Construction instructions
+ cInstEntryCPU("cr-link", &cHardwareCPU::Inst_CreateLink)
};
const int n_size = sizeof(s_n_array)/sizeof(cNOPEntryCPU);
@@ -3418,6 +3423,50 @@
*/
bool cHardwareCPU::Inst_CellID(cAvidaContext& ctx) {
const int reg_used = FindModifiedRegister(REG_BX);
- GetRegister(reg_used) = m_world->GetPopulation().GetCell(organism->GetOrgInterface().GetCellID()).GetRandomCellID();
+ GetRegister(reg_used) = m_world->GetPopulation().GetCell(organism->GetCellID()).GetRandomCellID();
return true;
}
+
+
+/*! Creates a link between cells, a form of distributed construction.
+
+Going to try something a little different here, and put all the logic for the link
+creation in the instruction, rather than in an organism or deme.
+*/
+bool cHardwareCPU::Inst_CreateLink(cAvidaContext& ctx) {
+ if(organism->GetCellID()==-1) return false;
+ cPopulationCell& cell = m_world->GetPopulation().GetCell(organism->GetCellID());
+ cDeme& deme = m_world->GetPopulation().GetDeme(cell.GetDemeID());
+ cDeme::Network& network = deme.GetNetwork();
+ cDeme::CellVertexMap& cvMap = deme.GetCellVertexMap();
+
+ // What is the cell that we're trying to connect to?
+ int connectTo=0;
+ // First, do we have a label?
+ if(GetLabel().GetSize()) {
+ // Yes; get the cell to connect to from the register.
+ connectTo = GetRegister(FindModifiedRegister(REG_BX));
+ // Now, if this isn't a valid cell ID, fail.
+ if(!deme.IsCellID(connectTo)) return false;
+ } else {
+ // No; get the cell to connect to from our facing.
+ connectTo = cell.ConnectionList().GetFirst()->GetRandomCellID();
+ }
+
+ // Now, are this cell and the cell we're connecting to in the network? If no,
+ // add them; if yes, then get a ref to the vertex descriptors.
+ cDeme::CellVertexMap::iterator u = cvMap.find(cell.GetRandomCellID());
+ if(u == cvMap.end()) {
+ // Add this cell to the network.
+ u = cvMap.insert(std::make_pair(cell.GetRandomCellID(), boost::add_vertex(network))).first;
+ }
+ cDeme::CellVertexMap::iterator v = cvMap.find(connectTo);
+ if(v == cvMap.end()) {
+ // Add the other cell to the network.
+ v = cvMap.insert(std::make_pair(connectTo, boost::add_vertex(network))).first;
+ }
+
+ // Finally, add the edge. We're done.
+ boost::add_edge(u->second, v->second, network);
+ return true;
+}
Modified: branches/dkdev/source/cpu/cHardwareCPU.h
===================================================================
--- branches/dkdev/source/cpu/cHardwareCPU.h 2007-02-26 01:09:12 UTC (rev 1369)
+++ branches/dkdev/source/cpu/cHardwareCPU.h 2007-02-26 01:09:53 UTC (rev 1370)
@@ -476,6 +476,9 @@
bool Inst_SendMessage(cAvidaContext& ctx);
bool Inst_RetrieveMessage(cAvidaContext& ctx);
bool Inst_CellID(cAvidaContext& ctx);
+
+ // Construction
+ bool Inst_CreateLink(cAvidaContext& ctx);
};
Modified: branches/dkdev/source/main/cDeme.cc
===================================================================
--- branches/dkdev/source/main/cDeme.cc 2007-02-26 01:09:12 UTC (rev 1369)
+++ branches/dkdev/source/main/cDeme.cc 2007-02-26 01:09:53 UTC (rev 1370)
@@ -39,3 +39,9 @@
return cell_ids[pos];
}
+void cDeme::Reset()
+{
+ birth_count = 0;
+ m_network = Network();
+ m_cvMap = CellVertexMap();
+}
Modified: branches/dkdev/source/main/cDeme.h
===================================================================
--- branches/dkdev/source/main/cDeme.h 2007-02-26 01:09:12 UTC (rev 1369)
+++ branches/dkdev/source/main/cDeme.h 2007-02-26 01:09:53 UTC (rev 1370)
@@ -14,19 +14,18 @@
#ifndef cDeme_h
#define cDeme_h
-#ifndef tArray_h
+#include <boost/graph/adjacency_list.hpp>
+#include <map>
#include "tArray.h"
-#endif
class cDeme {
-private:
- tArray<int> cell_ids;
- int width; // How wide is the deme?
- int birth_count; // How many organisms have been born into deme since reset?
- int org_count; // How many organisms are currently in the deme?
-
public:
+ //! An ease-of-use typedef to support the distributed construction of a network.
+ typedef boost::adjacency_list<boost::setS, boost::vecS, boost::undirectedS> Network;
+ //! A map of cell IDs to vertex descriptors.
+ typedef std::map<int, Network::vertex_descriptor> CellVertexMap;
+
cDeme();
~cDeme();
@@ -39,7 +38,7 @@
int GetWidth() const { return width; }
int GetHeight() const { return cell_ids.GetSize() / width; }
- void Reset() { birth_count = 0; }
+ void Reset();
int GetBirthCount() const { return birth_count; }
void IncBirthCount() { birth_count++; }
@@ -49,6 +48,22 @@
bool IsEmpty() const { return org_count == 0; }
bool IsFull() const { return org_count == cell_ids.GetSize(); }
+
+ //! Accessor for the network object associated with this deme.
+ Network& GetNetwork() { return m_network; }
+ //! Accessor for the cell-vertex map; contains cell ID -> vertex_descriptor entries.
+ CellVertexMap& GetCellVertexMap() { return m_cvMap; }
+ //! Returns true if cell_id is a cell ID in this deme, false otherwise.
+ bool IsCellID(int cell_id) { return false; }
+
+private:
+ tArray<int> cell_ids;
+ int width; // How wide is the deme?
+ int birth_count; // How many organisms have been born into deme since reset?
+ int org_count; // How many organisms are currently in the deme?
+
+ Network m_network; //!< The network associated with this deme.
+ CellVertexMap m_cvMap; //!< A map of cell IDs to vertex descriptors.
};
#endif
Modified: branches/dkdev/source/main/cPopulation.cc
===================================================================
--- branches/dkdev/source/main/cPopulation.cc 2007-02-26 01:09:12 UTC (rev 1369)
+++ branches/dkdev/source/main/cPopulation.cc 2007-02-26 01:09:53 UTC (rev 1370)
@@ -41,9 +41,7 @@
#include <fstream>
#include <vector>
-#include <algorithm>
-#include <set>
-#include <functional>
+#include <boost/graph/connected_components.hpp>
#include <float.h>
#include <math.h>
@@ -64,7 +62,7 @@
{
// How many demes are requested?
int num_demes = m_world->GetConfig().NUM_DEMES.Get();
-
+
// Error checking for demes vs. non-demes setup.
const int birth_method = m_world->GetConfig().BIRTH_METHOD.Get();
if(num_demes > 0) {
@@ -107,7 +105,7 @@
deme_array[deme_id].Setup(deme_cells);
}
-
+
// Setup the topology.
// What we're doing here is chopping the cell_array up into num_demes pieces.
// Note that having 0 demes (one population) is the same as having 1 deme. Then
@@ -128,7 +126,7 @@
}
case nGeometry::CLIQUE: {
build_clique(&cell_array.begin()[i], &cell_array.begin()[i+deme_size],
- deme_size_x, deme_size_y);
+ deme_size_x, deme_size_y);
break;
}
default: {
@@ -155,7 +153,7 @@
res->GetOutflowY2() );
m_world->GetStats().SetResourceName(i, res->GetName());
}
-
+
// Give stats information about the environment...
const cTaskLib & task_lib = environment.GetTaskLib();
for (int i = 0; i < task_lib.GetSize(); i++) {
@@ -167,7 +165,7 @@
for (int i = 0; i < inst_set.GetSize(); i++) {
m_world->GetStats().SetInstName(i, inst_set.GetName(i));
}
-
+
// Load a clone if one is provided, otherwise setup start organism.
if (m_world->GetConfig().CLONE_FILE.Get() == "-" || m_world->GetConfig().CLONE_FILE.Get() == "") {
cGenome start_org = cInstUtil::LoadGenome(m_world->GetConfig().START_CREATURE.Get(), world->GetHardwareManager().GetInstSet());
@@ -209,7 +207,7 @@
const int parent_id = parent_organism.GetOrgInterface().GetCellID();
assert(parent_id >= 0 && parent_id < cell_array.GetSize());
cPopulationCell& parent_cell = cell_array[parent_id];
-
+
tArray<int> target_cells(child_array.GetSize());
// Loop through choosing the later placement of each child in the population.
@@ -292,7 +290,7 @@
if (target_organism->InjectHost(parent_cpu.GetLabel(), injected_code)) {
cInjectGenotype* child_genotype = parent_genotype;
-
+
// If the parent genotype is not correct for the child, adjust it.
if (parent_genotype == NULL || parent_genotype->GetGenome() != injected_code) {
child_genotype = m_world->GetClassificationManager().GetInjectGenotype(injected_code, parent_genotype);
@@ -338,7 +336,7 @@
// Update the contents of the target cell.
KillOrganism(target_cell);
target_cell.InsertOrganism(*in_organism);
-
+
// Setup the inputs in the target cell.
environment.SetupInputs(ctx, target_cell.input_array);
@@ -379,18 +377,18 @@
cOrganism* organism = in_cell.GetOrganism();
cGenotype* genotype = organism->GetGenotype();
m_world->GetStats().RecordDeath();
-
+
tList<tListNode<cSaleItem> >* sold_items = organism->GetSoldItems();
if (sold_items)
{
tListIterator<tListNode<cSaleItem> > sold_it(*sold_items);
tListNode<cSaleItem> * test_node;
-
+
while ( (test_node = sold_it.Next()) != NULL)
{
- tListIterator<cSaleItem> market_it(market[test_node->data->GetLabel()]);
- market_it.Set(test_node);
- delete market_it.Remove();
+ tListIterator<cSaleItem> market_it(market[test_node->data->GetLabel()]);
+ market_it.Set(test_node);
+ delete market_it.Remove();
}
}
// Do the lineage handling
@@ -402,19 +400,19 @@
deme_array[in_cell.GetDemeID()].DecOrgCount();
}
genotype->RemoveOrganism();
-
+
for (int i = 0; i < organism->GetNumParasites(); i++) {
organism->GetParasite(i).RemoveParasite();
}
-
+
// And clear it!
in_cell.RemoveOrganism();
if (!organism->IsRunning()) delete organism;
else organism->GetPhenotype().SetToDelete();
-
+
// Alert the scheduler that this cell has a 0 merit.
schedule->Adjust(in_cell.GetID(), cMerit(0));
-
+
// Update the archive (note: genotype adjustment may be defered)
m_world->GetClassificationManager().AdjustGenotype(*genotype);
}
@@ -469,7 +467,7 @@
// find list under appropriate label, labels more than 8 nops long are simply the same
// as a smaller label modded by the market size
//int pos = label % market.GetSize();
-
+
//// id of genotype currently residing in cell that seller live(d) in compared to
//// id of genotype of actual seller, if different than seller is dead, remove item from list
//while ( market[pos].GetSize() > 0 &&
@@ -479,15 +477,15 @@
//{
// market[pos].Pop();
//}
-
+
// create sale item
cSaleItem *new_item = new cSaleItem(data, label, sell_price, org_id, cell_id);
-
+
// place into array by label, array is big enough for labels up to 8 nops long
tListNode<cSaleItem>* sell_node = market[label].PushRear(new_item);
tListNode<tListNode<cSaleItem> >* org_node = GetCell(cell_id).GetOrganism()->AddSoldItem(sell_node);
sell_node->data->SetNodePtr(org_node);
-
+
//:7 for Kolby
}
@@ -496,7 +494,7 @@
// find list under appropriate label, labels more than 8 nops long are simply the same
// as a smaller label modded by the market size
//int pos = label % market.GetSize();
-
+
//// id of genotype currently residing in cell that seller live(d) in compared to
//// id of genotype of actual seller, if different than seller is dead, remove item from list
//while ( market[pos].GetSize() > 0 &&
@@ -506,25 +504,25 @@
//{
// market[pos].Pop();
//}
-
+
// if there's nothing in the list don't bother with rest
if (market[label].GetSize() <= 0)
return 0;
-
+
// if the sell price is higher than we're willing to pay no purchase made
if (market[label].GetFirst()->GetPrice() > buy_price)
return 0;
-
+
// if the buy price is higher than buying org's current merit no purchase made
if (GetCell(cell_id).GetOrganism()->GetPhenotype().GetMerit().GetDouble() < buy_price)
return 0;
-
+
// otherwise transaction should be completed!
cSaleItem* chosen = market[label].Pop();
tListIterator<tListNode<cSaleItem> > sold_it(*GetCell(chosen->GetCellID()).GetOrganism()->GetSoldItems());
sold_it.Set(chosen->GetNodePtr());
sold_it.Remove();
-
+
// first update sellers merit
double cur_merit = GetCell(chosen->GetCellID()).GetOrganism()->GetPhenotype().GetMerit().GetDouble();
cur_merit += buy_price;
@@ -533,8 +531,8 @@
// next remove sold item from list in market
//market[pos].Remove(chosen);
-
-
+
+
// finally return recieve value, buyer merit will be updated if return a valid value here
int receive_value = chosen->GetData();
return receive_value;
@@ -547,12 +545,12 @@
0: deme fitness = 1 (control, random deme selection)
1: deme fitness = number of births since last competition (default)
2: deme fitness = average organism fitness at the current update (uses parent's fitness, so
- does not work with donations)
+ does not work with donations)
3: deme fitness = average mutation rate at the current update
4: deme fitness = strong rank selection on (parents) fitness (2^-deme fitness rank)
5: deme fitness = average organism life (current, not parents) fitness (works with donations)
6: deme fitness = strong rank selection on life (current, not parents) fitness
-*/
+ */
// For ease of use, each organism
// is setup as if it we just injected into the population.
@@ -571,7 +569,7 @@
case 1: // deme fitness = number of births
// Determine the scale for fitness by totaling births across demes.
for (int deme_id = 0; deme_id < num_demes; deme_id++) {
- double cur_fitness = (double) deme_array[deme_id].GetBirthCount();
+ double cur_fitness = (double) deme_array[deme_id].GetBirthCount();
deme_fitness[deme_id] = cur_fitness;
total_fitness += cur_fitness;
}
@@ -579,12 +577,12 @@
case 2: // deme fitness = average organism fitness at the current update
for (int deme_id = 0; deme_id < num_demes; deme_id++) {
cDoubleSum single_deme_fitness;
- const cDeme & cur_deme = deme_array[deme_id];
+ const cDeme & cur_deme = deme_array[deme_id];
for (int i = 0; i < cur_deme.GetSize(); i++) {
int cur_cell = cur_deme.GetCellID(i);
if (cell_array[cur_cell].IsOccupied() == false) continue;
cPhenotype & phenotype =
- GetCell(cur_cell).GetOrganism()->GetPhenotype();
+ GetCell(cur_cell).GetOrganism()->GetPhenotype();
single_deme_fitness.Add(phenotype.GetFitness());
}
deme_fitness[deme_id] = single_deme_fitness.Ave();
@@ -594,12 +592,12 @@
case 3: // deme fitness = average mutation rate at the current update
for (int deme_id = 0; deme_id < num_demes; deme_id++) {
cDoubleSum single_deme_div_type;
- const cDeme & cur_deme = deme_array[deme_id];
+ const cDeme & cur_deme = deme_array[deme_id];
for (int i = 0; i < cur_deme.GetSize(); i++) {
int cur_cell = cur_deme.GetCellID(i);
if (cell_array[cur_cell].IsOccupied() == false) continue;
cPhenotype & phenotype =
- GetCell(cur_cell).GetOrganism()->GetPhenotype();
+ GetCell(cur_cell).GetOrganism()->GetPhenotype();
assert(phenotype.GetDivType()>0);
single_deme_div_type.Add(1/phenotype.GetDivType());
}
@@ -612,7 +610,7 @@
{
for (int deme_id = 0; deme_id < num_demes; deme_id++) {
cDoubleSum single_deme_fitness;
- const cDeme & cur_deme = deme_array[deme_id];
+ const cDeme & cur_deme = deme_array[deme_id];
for (int i = 0; i < cur_deme.GetSize(); i++) {
int cur_cell = cur_deme.GetCellID(i);
if (cell_array[cur_cell].IsOccupied() == false) continue;
@@ -640,11 +638,11 @@
total_fitness += deme_fitness[deme_id];
}
}
- break;
- case 5: // deme fitness = average organism life fitness at the current update
- for (int deme_id = 0; deme_id < num_demes; deme_id++) {
+ break;
+ case 5: // deme fitness = average organism life fitness at the current update
+ for (int deme_id = 0; deme_id < num_demes; deme_id++) {
cDoubleSum single_deme_life_fitness;
- const cDeme & cur_deme = deme_array[deme_id];
+ const cDeme & cur_deme = deme_array[deme_id];
for (int i = 0; i < cur_deme.GetSize(); i++) {
int cur_cell = cur_deme.GetCellID(i);
if (cell_array[cur_cell].IsOccupied() == false) continue;
@@ -653,14 +651,14 @@
}
deme_fitness[deme_id] = single_deme_life_fitness.Ave();
total_fitness += deme_fitness[deme_id];
- }
- break;
- case 6: // deme fitness = 2^(-deme life fitness rank) (same as 4, but with life fitness)
+ }
+ break;
+ case 6: // deme fitness = 2^(-deme life fitness rank) (same as 4, but with life fitness)
// first find all the deme fitness values ...
{
for (int deme_id = 0; deme_id < num_demes; deme_id++) {
cDoubleSum single_deme_life_fitness;
- const cDeme & cur_deme = deme_array[deme_id];
+ const cDeme & cur_deme = deme_array[deme_id];
for (int i = 0; i < cur_deme.GetSize(); i++) {
int cur_cell = cur_deme.GetCellID(i);
if (cell_array[cur_cell].IsOccupied() == false) continue;
@@ -687,7 +685,7 @@
}
total_fitness += deme_fitness[deme_id];
}
- break;
+ break;
}
}
@@ -736,7 +734,7 @@
cDeme & from_deme = deme_array[from_deme_id];
cDeme & to_deme = deme_array[to_deme_id];
-
+
// Do the actual copy!
for (int i = 0; i < from_deme.GetSize(); i++) {
int from_cell_id = from_deme.GetCellID(i);
@@ -752,7 +750,7 @@
for (int deme_id = 0; deme_id < num_demes; deme_id++) {
if (is_init[deme_id] == true) continue;
cDeme & cur_deme = deme_array[deme_id];
-
+
for (int i = 0; i < cur_deme.GetSize(); i++) {
int cur_cell_id = cur_deme.GetCellID(i);
if (cell_array[cur_cell_id].IsOccupied() == false) continue;
@@ -768,58 +766,73 @@
/* Check if any demes have met the critera to be replicated and do so.
- There are several bases this can be checked on:
+There are several bases this can be checked on:
- 0: 'all' - ...all non-empty demes in the population.
- 1: 'full_deme' - ...demes that have been filled up.
- 2: 'corners' - ...demes with upper left and lower right corners filled.
+0: 'all' - ...all non-empty demes in the population.
+1: 'full_deme' - ...demes that have been filled up.
+2: 'corners' - ...demes with upper left and lower right corners filled.
*/
void cPopulation::ReplicateDemes(int rep_trigger)
{
// Determine which demes should be replicated.
const int num_demes = GetNumDemes();
-
+
// Loop through all candidate demes...
for (int deme_id = 0; deme_id < num_demes; deme_id++) {
cDeme & source_deme = deme_array[deme_id];
-
+
// Test this deme to determine if it should be replicated. If not,
// continue on to the next deme.
switch (rep_trigger) {
- case 0: // CASE: Replicate all non-empty demes...
+ case 0: // CASE: Replicate all non-empty demes...
// If this deme is empt, continue looping...
- if (source_deme.IsEmpty()) continue;
- break;
- case 1: // Replicate all full demes...
- if (source_deme.IsFull() == false) continue;
- break;
- case 2: // Replicate all demes with the corners filled in.
+ if (source_deme.IsEmpty()) continue;
+ break;
+ case 1: // Replicate all full demes...
+ if (source_deme.IsFull() == false) continue;
+ break;
+ case 2: // Replicate all demes with the corners filled in.
{
- // The first and last IDs represent the two corners.
- const int id1 = source_deme.GetCellID(0);
- const int id2 = source_deme.GetCellID(source_deme.GetSize() - 1);
- if (cell_array[id1].IsOccupied() == false ||
- cell_array[id2].IsOccupied() == false) continue;
+ // The first and last IDs represent the two corners.
+ const int id1 = source_deme.GetCellID(0);
+ const int id2 = source_deme.GetCellID(source_deme.GetSize() - 1);
+ if (cell_array[id1].IsOccupied() == false ||
+ cell_array[id2].IsOccupied() == false) continue;
}
- break;
- default:
- cerr << "ERROR: Invalid replication trigger " << rep_trigger
- << " in cPopulation::ReplicateDemes()" << endl;
- continue;
+ break;
+ case 3: {
+ // Checks to see if the topology that has been built by this deme:
+ // 1) Contains a vertex for all cells in the deme.
+ // 2) Is completely connected.
+ cDeme::Network& network = source_deme.GetNetwork();
+ if(boost::num_vertices(network) != (unsigned int)source_deme.GetSize()) continue;
+ std::vector<int> components(boost::num_vertices(network));
+ int num_components = boost::connected_components(network, &components[0]);
+ if(num_components > 1) continue;
+
+ // Hm, ok, well we now have completely connected deme. We should really do some
+ // stats tracking now.
+ m_world->GetStats().ConnectedTopology(network);
+ break;
+ }
+ default:
+ cerr << "ERROR: Invalid replication trigger " << rep_trigger
+ << " in cPopulation::ReplicateDemes()" << endl;
+ continue;
}
-
+
// -- If we made it this far, we should replicate this deme --
-
+
cRandom & random = m_world->GetRandom();
-
+
// Choose a random organism from this deme...
int cell1_id = -1;
const int deme1_size = source_deme.GetSize();
while (cell1_id == -1 || cell_array[cell1_id].IsOccupied() == false) {
cell1_id = source_deme.GetCellID(random.GetUInt(deme1_size));
}
-
+
// Choose a random target deme to replicate to...
int target_id = deme_id;
while (target_id == deme_id) target_id = random.GetUInt(num_demes);
@@ -834,21 +847,25 @@
// And do the replication into the central cell of the target deme...
const int cell2_id = target_deme.GetCellID( deme2_size/2 );
InjectClone( cell2_id, *(cell_array[cell1_id].GetOrganism()) );
-
+
// Clear out the source deme to reset it
for (int i = 0; i < deme1_size; i++) {
KillOrganism(cell_array[ source_deme.GetCellID(i) ]);
}
-
+
// Inject the target offspring back into the source ID.
const int cell3_id = source_deme.GetCellID( deme1_size/2 );
InjectClone( cell3_id, *(cell_array[cell2_id].GetOrganism()) );
-
+
// Rotate both injected cells to face northwest.
cell_array[cell2_id].Rotate(
- cell_array[GridNeighbor(cell2_id, world_x, world_y, -1, -1)] );
+ cell_array[GridNeighbor(cell2_id, world_x, world_y, -1, -1)] );
cell_array[cell3_id].Rotate(
- cell_array[GridNeighbor(cell3_id, world_x, world_y, -1, -1)] );
+ cell_array[GridNeighbor(cell3_id, world_x, world_y, -1, -1)] );
+
+ // And reset both demes, in case they have any cleanup work to do.
+ source_deme.Reset();
+ target_deme.Reset();
}
}
@@ -874,7 +891,7 @@
{
cDeme & deme1 = deme_array[deme1_id];
cDeme & deme2 = deme_array[deme2_id];
-
+
for (int i = 0; i < deme1.GetSize(); i++) {
int from_cell = deme1.GetCellID(i);
int to_cell = deme2.GetCellID(i);
@@ -894,26 +911,26 @@
{
// Must spawn into a different deme.
assert(deme1_id != deme2_id);
-
+
const int num_demes = deme_array.GetSize();
-
+
// If the second argument is a -1, choose a deme at random.
cRandom & random = m_world->GetRandom();
while (deme2_id == -1 || deme2_id == deme1_id) {
deme2_id = random.GetUInt(num_demes);
}
-
+
// Make sure we have all legal values...
assert(deme1_id >= 0 && deme1_id < num_demes);
assert(deme2_id >= 0 && deme2_id < num_demes);
-
+
// Find the demes that we're working with.
cDeme & deme1 = deme_array[deme1_id];
cDeme & deme2 = deme_array[deme2_id];
-
+
// Make sure that the deme we're copying from has at least 1 organism.
assert(deme1.GetOrgCount() > 0);
-
+
// Determine the cell to copy from.
int cell1_id = deme1.GetCellID( random.GetUInt(deme1.GetSize()) );
while (cell_array[cell1_id].IsOccupied() == false) {
@@ -924,7 +941,7 @@
for (int i = 0; i < deme2.GetSize(); i++) {
KillOrganism(cell_array[ deme2.GetCellID(i) ]);
}
-
+
// And do the spawning.
int cell2_id = deme2.GetCellID( random.GetUInt(deme2.GetSize()) );
InjectClone( cell2_id, *(cell_array[cell1_id].GetOrganism()) );
@@ -1099,14 +1116,14 @@
else if (birth_method == POSITION_CHILD_DEME_RANDOM) {
const int deme_id = parent_cell.GetDemeID();
const int deme_size = deme_array[deme_id].GetSize();
-
+
int out_pos = m_world->GetRandom().GetUInt(deme_size);
int out_cell_id = deme_array[deme_id].GetCellID(out_pos);
while (parent_ok == false && out_cell_id == parent_cell.GetID()) {
out_pos = m_world->GetRandom().GetUInt(deme_size);
out_cell_id = deme_array[deme_id].GetCellID(out_pos);
}
-
+
deme_array[deme_id].IncBirthCount();
return GetCell(out_cell_id);
}
@@ -1284,16 +1301,16 @@
// Test what tasks this creatures has completed.
for (int j=0; j < m_world->GetEnvironment().GetTaskLib().GetSize(); j++) {
if (phenotype.GetCurTaskCount()[j] > 0)
- {
- stats.AddCurTask(j);
- stats.AddCurTaskQuality(j, phenotype.GetCurTaskQuality()[j]);
- }
+ {
+ stats.AddCurTask(j);
+ stats.AddCurTaskQuality(j, phenotype.GetCurTaskQuality()[j]);
+ }
if (phenotype.GetLastTaskCount()[j] > 0)
- {
- stats.AddLastTask(j);
- stats.AddLastTaskQuality(j, phenotype.GetLastTaskQuality()[j]);
- stats.IncTaskExeCount(j, phenotype.GetLastTaskCount()[j]);
- }
+ {
+ stats.AddLastTask(j);
+ stats.AddLastTaskQuality(j, phenotype.GetLastTaskQuality()[j]);
+ stats.IncTaskExeCount(j, phenotype.GetLastTaskCount()[j]);
+ }
}
// Increment the counts for all qualities the organism has...
@@ -1312,7 +1329,7 @@
// Increment the age of this organism.
organism->GetPhenotype().IncAge();
- }
+ }
stats.SetBreedTrueCreatures(num_breed_true);
stats.SetNumNoBirthCreatures(num_no_birth);
@@ -1334,7 +1351,7 @@
stats.SetResources(resource_count.GetResources());
stats.SetSpatialRes(resource_count.GetSpatialRes());
stats.SetResourcesGeometry(resource_count.GetResourcesGeometry());
- }
+}
void cPopulation::UpdateGenotypeStats()
@@ -1707,11 +1724,11 @@
}
}
cout << (*it).id_num << " "
- << (*it).parent_id << " "
- << (*it).genotype->GetParentID() << " "
- << (*it).genotype->GetNumOffspringGenotypes() << " "
- << (*it).num_cpus << " "
- << (*it).genotype->GetNumOrganisms() << endl;
+ << (*it).parent_id << " "
+ << (*it).genotype->GetParentID() << " "
+ << (*it).genotype->GetNumOffspringGenotypes() << " "
+ << (*it).num_cpus << " "
+ << (*it).genotype->GetNumOrganisms() << endl;
if (soup_full){
cout << "cPopulation::LoadDumpFile: You are trying to load more organisms than there is space!" << endl;
cout << "cPopulation::LoadDumpFile: Remaining organisms are ignored." << endl;
@@ -2051,7 +2068,7 @@
void cPopulation::PrintPhenotypeData(const cString& filename)
{
set<int> ids;
-
+
for (int i = 0; i < cell_array.GetSize(); i++) {
// Only look at cells with organisms in them.
if (cell_array[i].IsOccupied() == false) continue;
Modified: branches/dkdev/source/main/cStats.cc
===================================================================
--- branches/dkdev/source/main/cStats.cc 2007-02-26 01:09:12 UTC (rev 1369)
+++ branches/dkdev/source/main/cStats.cc 2007-02-26 01:09:53 UTC (rev 1370)
@@ -848,3 +848,21 @@
num_bought = num_sold = num_used = num_own_used = 0;
df.Endl();
}
+
+void cStats::ConnectedTopology(cDeme::Network& network) {
+ ++m_topo_numReplications;
+ m_topo_numEdges.Add(boost::num_edges(network));
+}
+
+
+void cStats::PrintTopologyData(const cString& filename) {
+ cDataFile& df = m_world->GetDataFile(filename);
+ df.WriteComment( "Topology data\n" );
+ df.WriteTimeStamp();
+ df.Write(GetUpdate(), "update" );
+ df.Write(m_topo_numReplications, "Number of deme replications.");
+ df.Write(m_topo_numEdges.Average(), "Avg. number of edges on deme replication.");
+ m_topo_numReplications = 0;
+ m_topo_numEdges.Clear();
+ df.Endl();
+}
Modified: branches/dkdev/source/main/cStats.h
===================================================================
--- branches/dkdev/source/main/cStats.h 2007-02-26 01:09:12 UTC (rev 1369)
+++ branches/dkdev/source/main/cStats.h 2007-02-26 01:09:53 UTC (rev 1370)
@@ -40,6 +40,8 @@
#include "nGeometry.h"
#endif
+#include "cDeme.h"
+
class cGenotype;
class cInjectGenotype;
class cWorld;
@@ -215,6 +217,9 @@
int num_sold;
int num_used;
int num_own_used;
+
+ int m_topo_numReplications; //!< Number of deme replications since the last stats output.
+ cDoubleSum m_topo_numEdges; //!< Average number of edges per deme upon replication.
cStats(); // @not_implemented
cStats(const cStats&); // @not_implemented
@@ -558,6 +563,11 @@
void PrintInstructionData(const cString& filename);
void PrintGenotypeMap(const cString& filename);
void PrintMarketData(const cString& filename);
+
+ // Topology
+ void ConnectedTopology(cDeme::Network& network);
+ void PrintTopologyData(const cString& filename);
+
};
More information about the Avida-cvs
mailing list