Skip to content
Snippets Groups Projects
Commit d70fc3ee authored by AxelCarayon's avatar AxelCarayon
Browse files

refactoring to make code more generic

parent 5aef0044
No related branches found
No related tags found
No related merge requests found
Showing
with 390 additions and 44 deletions
......@@ -20,6 +20,8 @@
*.rar
src/main/resources/output.csv
src/main/resources/pythonOutput/*.csv
src/main/resources/pythonOutput/*.png
# virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml
hs_err_pid*
......@@ -127,7 +127,7 @@
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
5. Submission of Contributions. Unless You explicitly SEIRSState otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
......
import csv
import yaml
import matplotlib.pyplot as plt
OUTPUT_FILE_LOCATION = 'src/main/resources/output.csv'
OUTPUT_FOLDER = 'src/main/resources/pythonOutput'
JAR_LOCATION = 'out/artifacts/SMA_SEIR_jar/SMA-SEIR.jar'
YAML_FILE = 'src/main/resources/parameters.yaml'
def readCSV(fileName):
with open(fileName, 'r') as csvfile:
reader = csv.reader(csvfile)
return list(reader)
def showDiagram(data):
def getValues() :
with open(YAML_FILE, 'r') as file:
data = yaml.safe_load(file)
incubation = data['incubationRate']
infection = data['infectionRate']
recovery = data['recoveryRate']
looseImmunity = data['looseImmunityRate']
return f"incubationRate : {incubation} InfectionRate : {infection}\n RecoveryRate : {recovery} LooseImmunityRate : {looseImmunity}"
def makeDiagram(fileName):
data = readCSV(fileName)
suceptible = []
exposed = []
recovred = []
......@@ -18,6 +34,7 @@ def showDiagram(data):
recovred.append(int(row[2]))
infected.append(int(row[3]))
plt.title(getValues())
plt.plot(suceptible, label='Suceptible', color='gray')
plt.plot(exposed, label='Exposed', color='yellow')
plt.plot(infected, label='Infected', color='red')
......@@ -25,14 +42,36 @@ def showDiagram(data):
plt.xlabel('Cycles')
plt.ylabel('Peoples')
plt.legend()
plt.show()
plt.savefig(f'{fileName.split(".")[0]}.png')
#plt.show()
plt.close()
def runJavaJar(fileName):
import subprocess
subprocess.call(['java', '-jar', fileName])
def copyToOutputFolder(fileName):
import shutil
shutil.copy(OUTPUT_FILE_LOCATION, f"{OUTPUT_FOLDER}/{fileName}")
def createFile():
with open(OUTPUT_FILE_LOCATION, 'w') as file:
file.write('')
def editYaml(key,value):
with open(YAML_FILE, 'r') as file:
data = yaml.safe_load(file)
data[key] = value
runJavaJar('out/artifacts/SMA_SEIR_jar/SMA-SEIR.jar')
with open(YAML_FILE, 'w') as file:
yaml.dump(data, file)
# data = readCSV("src/main/resources/output.csv")
# if __name__ == "__main__":
# for i in range(10):
# editYaml("infectionRate", 0.05+(0.05*i))
# runJavaJar(JAR_LOCATION)
# copyToOutputFolder(f"output{i}.csv")
# makeDiagram(f"{OUTPUT_FOLDER}/output{i}.csv")
# showDiagram(data)
\ No newline at end of file
runJavaJar(JAR_LOCATION)
makeDiagram(OUTPUT_FILE_LOCATION)
\ No newline at end of file
import agents.RandomWalkingAgent;
import agents.SEIRSAgent;
import agents.states.InfectedSEIRSState;
import environment.SEIRSEnvironment;
import models.Parameters;
import scheduler.FairAsynchronousScheduler;
import scheduler.FairSynchronousScheduler;
import scheduler.Scheduler;
import sma.SEIRS_SMA;
import sma.SMA;
import utils.YamlReader;
import java.awt.*;
import java.util.Random;
public class RunExperiment {
public static void main(String[] args) {
SMA sma = new SEIRS_SMA();
Parameters parameters = YamlReader.getParams();
Random r = new Random(parameters.getSeed());
SEIRSAgent[] agents = new RandomWalkingAgent[parameters.getPopulation()];
Scheduler scheduler;
SEIRSEnvironment environment = new SEIRSEnvironment(parameters.getSize(),agents);
//Populate agents
for (int i = 0; i<parameters.getPopulation();i++) {
Point position = new Point(r.nextInt(parameters.getSize()),r.nextInt(parameters.getSize()));
RandomWalkingAgent agent = new RandomWalkingAgent(position,parameters.getSeed()+i,environment);
agents[i] = agent;
}
//Infect agents
for (int i=0 ; i< parameters.getNbOfPatientZero(); i++) {
SEIRSAgent agent = agents[(r.nextInt(parameters.getPopulation()))];
while (agent.getState() instanceof InfectedSEIRSState) {
agent = agents[(r.nextInt(parameters.getPopulation()))];
}
agent.changeState(new InfectedSEIRSState(agent));
}
//create scheduler
if (parameters.isSynchronousMode()) {
scheduler = new FairSynchronousScheduler(parameters.getSeed());
} else {
scheduler = new FairAsynchronousScheduler();
}
sma.init(environment,scheduler,agents);
sma.run();
}
}
package agents;
public interface Agent {
void wakeUp();
}
package agents;
import java.awt.*;
public interface Agent2D extends Agent {
Point getPosition();
}
package sma.agents;
package agents;
import sma.agents.states.InfectedState;
import sma.agents.states.State;
import sma.agents.states.SuceptibleState;
import sma.environment.Environment;
import sma.environment.SquaredChunksEnvironment;
import agents.states.InfectedSEIRSState;
import agents.states.SEIRSState;
import agents.states.SuceptibleSEIRSState;
import environment.SquareEnvironment2D;
import environment.SEIRSEnvironment;
import utils.YamlReader;
import java.awt.Point;
import java.util.Random;
public class RandomWalkingAgent implements Agent {
public class RandomWalkingAgent implements SEIRSAgent {
private Point position;
private Random r;
private SquaredChunksEnvironment environment;
private State state;
private final Random r;
private final SEIRSEnvironment environment;
private SEIRSState SEIRSState;
public RandomWalkingAgent(Point position, int seed, SquaredChunksEnvironment environment) {
public RandomWalkingAgent(Point position, int seed, SEIRSEnvironment environment) {
this.position = position;
this.state = new SuceptibleState(this);
this.SEIRSState = new SuceptibleSEIRSState(this);
this.environment = environment;
this.r = new Random(seed);
}
public void move() {
state.onMovement();
private void move() {
SEIRSState.onMovement();
int move = r.nextInt(4);
Point newPosition = switch (move) {
case Environment.LEFT -> new Point(position.x-environment.RADIUS,position.y);
case Environment.RIGHT -> new Point(position.x+environment.RADIUS,position.y);
case Environment.UP -> new Point(position.x,position.y-environment.RADIUS);
case Environment.DOWN -> new Point(position.x,position.y+environment.RADIUS);
case SquareEnvironment2D.LEFT -> new Point(position.x- SEIRSEnvironment.RADIUS,position.y);
case SquareEnvironment2D.RIGHT -> new Point(position.x+ SEIRSEnvironment.RADIUS,position.y);
case SquareEnvironment2D.UP -> new Point(position.x,position.y- SEIRSEnvironment.RADIUS);
case SquareEnvironment2D.DOWN -> new Point(position.x,position.y+ SEIRSEnvironment.RADIUS);
default -> throw new IllegalStateException("Unexpected value: " + move);
};
if (newPosition.x <= environment.size-1 && newPosition.x >= 0 && newPosition.y <= environment.size-1 && newPosition.y >=0 ) {
environment.notifyNewPosition(position,newPosition,this);
if (newPosition.x <= environment.getSize()-1 && newPosition.x >= 0 && newPosition.y <= environment.getSize()-1 && newPosition.y >=0 ) {
environment.notifyNewPosition(position,newPosition ,this);
position = newPosition;
}
}
@Override
public void changeState(State state) { this.state = state; }
public void wakeUp() {
move();
}
@Override
public void changeState(SEIRSState SEIRSState) { this.SEIRSState = SEIRSState; }
@Override
public boolean isExposed() {
boolean isExposed = false;
for (Agent neighbor: environment.getNeighbors(position)) {
if (neighbor.getState() instanceof InfectedState) {
int roll = r.nextInt(100)+1;
if (roll <= YamlReader.getParams().getInfectionRate()*100) {
for (SEIRSAgent neighbor: environment.getNeighbors(position)) {
if ((neighbor).getState() instanceof InfectedSEIRSState) {
int roll = r.nextInt(10000)+1;
if (roll <= YamlReader.getParams().getInfectionRate()*10000) {
isExposed = true;
}
}
......@@ -60,8 +66,8 @@ public class RandomWalkingAgent implements Agent {
@Override
public boolean isInfected() {
boolean isSick = false;
int roll = r.nextInt(100)+1;
if (roll <= YamlReader.getParams().getIncubationRate()*100) {
int roll = r.nextInt(10000)+1;
if (roll <= YamlReader.getParams().getIncubationRate()*10000) {
isSick = true;
}
return isSick;
......@@ -70,8 +76,8 @@ public class RandomWalkingAgent implements Agent {
@Override
public boolean isRecovered() {
boolean isHealed = false;
int roll = r.nextInt(100)+1;
if (roll <= YamlReader.getParams().getRecoveryRate()*100) {
int roll = r.nextInt(10000)+1;
if (roll <= YamlReader.getParams().getRecoveryRate()*10000) {
isHealed = true;
}
return isHealed;
......@@ -80,15 +86,15 @@ public class RandomWalkingAgent implements Agent {
@Override
public boolean hasLostImmunity() {
boolean hasLostImmunity = false;
int roll = r.nextInt(100)+1;
if (roll <= YamlReader.getParams().getLooseImmunityRate()*100) {
int roll = r.nextInt(10000)+1;
if (roll <= YamlReader.getParams().getLooseImmunityRate()*10000) {
hasLostImmunity = true;
}
return hasLostImmunity;
}
@Override
public State getState() { return this.state; }
public SEIRSState getState() { return this.SEIRSState; }
@Override
public Point getPosition() { return position; }
......
package sma.agents;
package agents;
import sma.agents.states.State;
import agents.states.SEIRSState;
import java.awt.*;
public interface SEIRSAgent extends Agent2D {
public interface Agent {
void changeState(State state);
State getState();
void changeState(SEIRSState SEIRSState);
SEIRSState getState();
boolean isExposed();
boolean isInfected();
boolean isRecovered();
boolean hasLostImmunity();
void move();
Point getPosition();
}
package sma.agents.states;
package agents.states;
import sma.agents.Agent;
public class ExposedSEIRSState extends SEIRSState {
public class ExposedState extends State{
public ExposedState(Agent agent) {
super(agent);
public ExposedSEIRSState(agents.SEIRSAgent SEIRSAgent) {
super(SEIRSAgent);
}
@Override
public void onMovement() {
if (agent.isInfected()) {
agent.changeState(new InfectedState(agent));
agent.changeState(new InfectedSEIRSState(agent));
}
}
......
package sma.agents.states;
package agents.states;
import sma.agents.Agent;
public class InfectedSEIRSState extends SEIRSState {
public class InfectedState extends State{
public InfectedState(Agent agent) {
super(agent);
public InfectedSEIRSState(agents.SEIRSAgent SEIRSAgent) {
super(SEIRSAgent);
}
@Override
public void onMovement() {
if (agent.isRecovered()) {
agent.changeState(new RecoveredState(agent));
agent.changeState(new RecoveredSEIRSState(agent));
}
}
......
package sma.agents.states;
package agents.states;
import sma.agents.Agent;
import agents.SEIRSAgent;
public class RecoveredState extends State{
public class RecoveredSEIRSState extends SEIRSState {
public RecoveredState(Agent agent) {
super(agent);
public RecoveredSEIRSState(SEIRSAgent SEIRSAgent) {
super(SEIRSAgent);
}
@Override
public void onMovement() {
if (agent.hasLostImmunity()) {
agent.changeState(new SuceptibleState(agent));
agent.changeState(new SuceptibleSEIRSState(agent));
}
}
......
package sma.agents.states;
package agents.states;
import sma.agents.Agent;
import agents.SEIRSAgent;
public abstract class State {
public abstract class SEIRSState {
public final static String EXPOSED = "EXPOSED";
public final static String INFECTED = "INFECTED";
public final static String SUCEPTIBLE = "SUCEPTIBLE";
public final static String RECOVERED = "RECOVERED";
protected Agent agent;
protected final agents.SEIRSAgent agent;
State(Agent agent) {
SEIRSState(SEIRSAgent agent) {
this.agent = agent;
}
......
package sma.agents.states;
package agents.states;
import sma.agents.Agent;
public class SuceptibleSEIRSState extends SEIRSState {
import java.awt.*;
public class SuceptibleState extends State{
public SuceptibleState(Agent agent) {
super(agent);
public SuceptibleSEIRSState(agents.SEIRSAgent SEIRSAgent) {
super(SEIRSAgent);
}
@Override
public void onMovement() {
if (agent.isExposed()) {
agent.changeState(new ExposedState(agent));
agent.changeState(new ExposedSEIRSState(agent));
}
}
......
package environment;
public interface Environment {
}
package environment;
import agents.Agent;
import java.awt.*;
public interface Environment2D extends Environment {
void notifyNewPosition(Point oldPosition, Point newPosition, Agent agent);
}
package sma.environment;
package environment;
import sma.agents.Agent;
import sma.agents.states.State;
import agents.Agent;
import agents.SEIRSAgent;
import agents.states.SEIRSState;
import java.awt.*;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
public class SquaredChunksEnvironment implements Environment {
@SuppressWarnings("unchecked")
public class SEIRSEnvironment implements SquareEnvironment2D {
public final static int RADIUS = 10;
public final static int CHUNK_SIZE = 2*RADIUS;
public int size;
private Agent[] agents;
private List<Agent>[][] chunks;
public final int size;
private final SEIRSAgent[] agents;
private List<SEIRSAgent>[][] chunks;
public SquaredChunksEnvironment(int size, Agent[] agents) {
public SEIRSEnvironment(int size, SEIRSAgent[] agents) {
this.agents = agents;
this.size = size;
}
......@@ -29,7 +31,7 @@ public class SquaredChunksEnvironment implements Environment {
chunks[i][j] = new ArrayList<>();
}
}
for (Agent agent : agents) {
for (SEIRSAgent agent : agents) {
int x = agent.getPosition().x/CHUNK_SIZE;
int y = agent.getPosition().y/CHUNK_SIZE;
chunks[x][y].add(agent);
......@@ -57,12 +59,12 @@ public class SquaredChunksEnvironment implements Environment {
};
}
private List<Agent> getChunkNeighbors(int relativeTo, Point p) {
private List<SEIRSAgent> getChunkNeighbors(int relativeTo, Point p) {
Point newPosition = getRelativePoint(relativeTo,p);
Point chunk = new Point(newPosition.x/CHUNK_SIZE,newPosition.y/CHUNK_SIZE);
var neighbors = new ArrayList<Agent>();
List<SEIRSAgent> neighbors = new ArrayList<>();
try{
for (Agent agent : chunks[chunk.x][chunk.y]) {
for (SEIRSAgent agent : chunks[chunk.x][chunk.y]) {
if (detectCollision(p, agent.getPosition())) {
neighbors.add(agent);
}
......@@ -73,12 +75,11 @@ public class SquaredChunksEnvironment implements Environment {
return neighbors;
}
@Override
public List<Agent> getNeighbors(Point position) {
public List<SEIRSAgent> getNeighbors(Point position) {
if (chunks == null) {
throw new IllegalStateException("Chunks aren't initialized, you should use the initiateMethod() first.");
}
var neighbors = new ArrayList<Agent>();
var neighbors = new ArrayList<SEIRSAgent>();
for (int i = 0; i < MAX_CHUNK; i++) {
neighbors.addAll(getChunkNeighbors(i,position));
......@@ -86,30 +87,33 @@ public class SquaredChunksEnvironment implements Environment {
return neighbors;
}
@Override
public void notifyNewPosition(Point oldPosition, Point newPosition, Agent agent) {
if (chunks == null) {
throw new IllegalStateException("Chunks aren't initialized, you should use the initiateMethod() first.");
}
if (oldPosition.x/CHUNK_SIZE != newPosition.x/CHUNK_SIZE || oldPosition.y/CHUNK_SIZE != newPosition.y/CHUNK_SIZE) {
chunks[oldPosition.x/CHUNK_SIZE][oldPosition.y/CHUNK_SIZE].remove(agent);
chunks[newPosition.x/CHUNK_SIZE][newPosition.y/CHUNK_SIZE].add(agent);
chunks[oldPosition.x/CHUNK_SIZE][oldPosition.y/CHUNK_SIZE].remove((SEIRSAgent) agent);
chunks[newPosition.x/CHUNK_SIZE][newPosition.y/CHUNK_SIZE].add((SEIRSAgent) agent);
}
}
@Override
public HashMap<String,Integer> getAgentStatus() {
var map = new HashMap<String,Integer>();
map.put(State.EXPOSED,0);
map.put(State.INFECTED,0);
map.put(State.RECOVERED,0);
map.put(State.SUCEPTIBLE,0);
map.put(SEIRSState.EXPOSED,0);
map.put(SEIRSState.INFECTED,0);
map.put(SEIRSState.RECOVERED,0);
map.put(SEIRSState.SUCEPTIBLE,0);
for (Agent agent : agents) {
String state = agent.getState().toString();
for (SEIRSAgent SEIRSAgent : agents) {
String state = SEIRSAgent.getState().toString();
map.put(state,map.get(state)+1);
}
return map;
}
@Override
public int getSize() {
return size;
}
}
package sma.environment;
package environment;
import sma.agents.Agent;
import java.awt.Point;
import java.util.HashMap;
import java.util.List;
public interface Environment {
public interface SquareEnvironment2D extends Environment2D {
int LEFT = 0;
int RIGHT = 1;
int UP = 2;
......@@ -18,7 +12,5 @@ public interface Environment {
int DOWN_RIGHT = 8;
int MAX_CHUNK = 9;
List<Agent> getNeighbors(Point position);
void notifyNewPosition(Point oldPosition, Point newPosition, Agent agent);
HashMap<String,Integer> getAgentStatus();
int getSize();
}
package models;
@SuppressWarnings("unused")
public class Parameters {
private int seed;
......
package scheduler;
public abstract class AsynchronousScheduler implements Scheduler {
}
package sma.scheduler;
package scheduler;
import sma.agents.Agent;
import sma.agents.RandomWalkingAgent;
import agents.Agent;
import java.util.Arrays;
import java.util.List;
......@@ -10,17 +9,19 @@ import java.util.concurrent.*;
import java.util.function.Function;
import java.util.stream.Collectors;
public class FairAsynchronousScheduler implements Scheduler{
public class FairAsynchronousScheduler extends AsynchronousScheduler {
private ExecutorService executor = Executors.newSingleThreadExecutor();
private final ExecutorService executor = Executors.newSingleThreadExecutor();
private Queue<Agent> queue;
public FairAsynchronousScheduler(Agent[] agents) {
@Override
public void init(Agent[] agents) {
this.queue = new ConcurrentLinkedQueue<>(Arrays.stream(agents).toList());
}
public void nextCycle() {
List<Future<Agent>> results = queue.parallelStream().map(agent -> executor.submit(() -> {agent.move(); return agent;})).toList();
@Override
public void doNextCycle() {
List<Future<Agent>> results = queue.parallelStream().map(agent -> executor.submit(() -> {agent.wakeUp(); return agent;})).toList();
Function<Future<Agent>, Agent> futureTreatment = futureAgent -> {
try {
return futureAgent.get();
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment