package com.framsticks.standard; import java.util.LinkedList; import java.util.List; import java.util.Random; import java.util.TimerTask; import com.framsticks.experiment.Experiment; import com.framsticks.experiment.Simulator; import com.framsticks.model.Genotype; import com.framsticks.params.Access; import com.framsticks.params.EventListener; import com.framsticks.params.Registry; import com.framsticks.params.annotations.FramsClassAnnotation; import com.framsticks.structure.messages.ListChange; import com.framsticks.util.dispatching.Dispatching; import com.framsticks.util.dispatching.Future; import org.apache.logging.log4j.Logger; import org.apache.logging.log4j.LogManager; @FramsClassAnnotation public class StandardExperiment extends Experiment { private static final Logger log = LogManager.getLogger(StandardExperiment.class); protected final Registry registry = new Registry(); protected List genotypes = new LinkedList<>(); protected Random random = new Random(); // @ParamAnnotation // protected final NetLoadSaveLogic netLoadSaveLogic; /** * */ public StandardExperiment() { setExpdef("standard"); registry.registerAndBuild(StandardState.class); addSimulatorsListener(new EventListener() { @Override public void action(final ListChange change) { assert isActive(); final Simulator simulator = getSimulators().get(change.getIdentifier()); if (change.getAction().equals(ListChange.Action.Add)) { simulator.init(); return; } if (change.getAction().equals(ListChange.Action.Modify)) { if (change.hasHint("ready")) { log.debug("issuing netsave"); simulator.netsave(StandardState.class, new Future(StandardExperiment.this) { @Override protected void result(StandardState result) { assert isActive(); assert result != null; processState(simulator, result); simulator.netload(result, new Future(StandardExperiment.this) { @Override protected void result(Object result) { runSimulatorFor(simulator); } }); } }); } return; } } }); // netLoadSaveLogic = new NetLoadSaveLogic(this, StandardState.class) { // @Override // public void netload(Simulator simulator, FutureHandler net) { // assert isActive(); // // Dispatching.sleep(0.1); // net.pass(null); // // simulator.start(); // } // @Override // public void netsave(Simulator simulator, StandardState net) { // assert isActive(); // log.debug("saved state: {}", net); // runSimulatorFor(simulator); // } // }; } protected void processState(Simulator simulator, StandardState state) { Access genePoolAccess = registry.bindAccessFor(state.genepools.get(0)); Access genotypesAccess = registry.bindAccessFor(genePoolAccess, "genotypes"); int count = genotypesAccess.getParamCount(); int toRemove = count / 10; log.debug("processing state {} for simulator {} with {} genotypes", state, simulator, count); List removed = new LinkedList<>(); for (int c = 0; c < toRemove; ++c) { int number = random.nextInt(genotypesAccess.getParamCount()); Genotype genotype = genotypesAccess.get(number, Genotype.class); genotypesAccess.set(number, null); log.debug("removing {} from {}", genotype, simulator); removed.add(genotype); } int toAdd = toRemove; if (toAdd > genotypes.size()) { toAdd = genotypes.size(); } if (genotypes.size() > 100) { toAdd = genotypes.size() - 100; } for (int a = 0; (a < toAdd) && (!genotypes.isEmpty()); ++a) { Genotype genotype = genotypes.remove(0); log.debug("adding {} to {}", genotype, simulator); genotype.uid = null; genotypesAccess.set((String) null, genotype); } log.debug("state processed"); genotypes.addAll(removed); } protected void runSimulatorFor(final Simulator simulator) { simulator.start(); Dispatching.getTimer().schedule(new TimerTask() { @Override public void run() { simulator.stop(); } }, 2000); } }