Browse Source

Letzter commit für Bachelorarbeit

Dominik Rieder 5 years ago
parent
commit
edad0af3fb
34 changed files with 1791 additions and 491 deletions
  1. BIN
      res/Images/wildCard.png
  2. BIN
      res/Images/wildCard2.png
  3. BIN
      res/Images/wildCard3.png
  4. 5 0
      src/algorithms/geneticAlgorithm/Components/GAIndividual.java
  5. 1 2
      src/algorithms/geneticAlgorithm/Components/GAMutationStrategy.java
  6. 18 7
      src/algorithms/geneticAlgorithm/Components/GeneticAlgo.java
  7. 194 0
      src/algorithms/geneticAlgorithm/Components/Selections/TournamentProportionalSelection.java
  8. 6 2
      src/algorithms/geneticAlgorithm/Components/Selections/TournamentRankSelection.java
  9. 40 0
      src/algorithms/geneticAlgorithm/holegGA/Components/AlgoRunnable.java
  10. 43 66
      src/algorithms/geneticAlgorithm/holegGA/Components/HolegCrossover.java
  11. 57 11
      src/algorithms/geneticAlgorithm/holegGA/Components/HolegFactory.java
  12. 43 18
      src/algorithms/geneticAlgorithm/holegGA/Components/HolegFittnessFkt.java
  13. 186 5
      src/algorithms/geneticAlgorithm/holegGA/Components/HolegFittnessScenario.java
  14. 4 1
      src/algorithms/geneticAlgorithm/holegGA/Components/HolegGeneration.java
  15. 96 33
      src/algorithms/geneticAlgorithm/holegGA/Components/HolegIndividual.java
  16. 144 107
      src/algorithms/geneticAlgorithm/holegGA/Components/HolegMutation.java
  17. 222 0
      src/algorithms/geneticAlgorithm/holegGA/Evaluator.java
  18. 9 0
      src/algorithms/geneticAlgorithm/holegGA/GAEdge.java
  19. 68 136
      src/algorithms/geneticAlgorithm/holegGA/GenAlgoHandler.java
  20. 174 1
      src/algorithms/geneticAlgorithm/holegGA/GenAlgoInit.java
  21. 249 77
      src/algorithms/geneticAlgorithm/holegGA/GenAlgoWindow.java
  22. 43 0
      src/algorithms/geneticAlgorithm/holegGA/ParameterArray.java
  23. 8 8
      src/classes/AbstractCpsObject.java
  24. 37 0
      src/classes/HolonWildCard.java
  25. 3 0
      src/classes/SubNet.java
  26. 5 5
      src/ui/controller/CanvasController.java
  27. 7 0
      src/ui/controller/CategoryController.java
  28. 11 0
      src/ui/controller/Control.java
  29. 1 1
      src/ui/controller/NodeController.java
  30. 25 3
      src/ui/controller/SimulationManager.java
  31. 13 1
      src/ui/view/AlgorithmMenu.java
  32. 29 3
      src/ui/view/GUI.java
  33. 49 3
      src/ui/view/NewPopUp.java
  34. 1 1
      tests/tests/PraktikumHolonsTestCanvasController.java

BIN
res/Images/wildCard.png


BIN
res/Images/wildCard2.png


BIN
res/Images/wildCard3.png


+ 5 - 0
src/algorithms/geneticAlgorithm/Components/GAIndividual.java

@@ -11,4 +11,9 @@ public class GAIndividual {
 	public void setFittness(double fittness){
 		this.fittness = fittness;
 	}
+	
+	
+	public void addLogEntry(String text){
+		
+	}
 }

+ 1 - 2
src/algorithms/geneticAlgorithm/Components/GAMutationStrategy.java

@@ -5,11 +5,10 @@ import java.util.Random;
 public abstract class GAMutationStrategy<I extends GAIndividual> {
 	
 	protected double mutationProb;
-	protected Random rng;
+	protected static Random rng = new Random();
 	
 	public GAMutationStrategy(double prob){
 		mutationProb = prob;
-		rng = new Random();
 	}
 	
 	public GAMutationStrategy(){

+ 18 - 7
src/algorithms/geneticAlgorithm/Components/GeneticAlgo.java

@@ -5,7 +5,7 @@ import java.util.Random;
 
 import algorithms.geneticAlgorithm.holegGA.Components.HolegIndividual;
 
-public class GeneticAlgo<I extends GAIndividual> {
+public class GeneticAlgo<I extends HolegIndividual> {
 
 	public int popSize;
 	public ArrayList<I> population;
@@ -29,8 +29,7 @@ public class GeneticAlgo<I extends GAIndividual> {
 		this.popSize = popSize;
 		
 		population = new ArrayList<I>();
-		topPercent = 0.1;
-		buttomPercent = 0.95;
+		topPercent = 0.0;
 		
 		//generateRandomPopulation();
 	}
@@ -45,12 +44,23 @@ public class GeneticAlgo<I extends GAIndividual> {
 	
 	public void createNextGeneration(){
 		ArrayList<I> nextGen = new ArrayList<I>();
+		
+		
 		int topBound = (int) Math.ceil(topPercent * popSize);
-		population = sortPopulation(population);
-		nextGen.addAll(population.subList(0, topBound));
+		//int topBound = 1;
+		population = getSortedPopulation();
 		
-		int buttomBound = (int) Math.ceil(buttomPercent * popSize);
-		nextGen.addAll(population.subList(buttomBound, population.size()));
+		for(I individual : population.subList(0, topBound)){
+			ArrayList<I> childs = new ArrayList<I>();
+			childs.add(individual);
+			childs.add(individual);
+			childs = reproducer.crossOver(childs);
+			for(I i : childs){
+				i.addLogEntry("Top % from previous gen");
+				fittnessFunction.calculateFittness(i);
+				nextGen.add(i);
+			}
+		}
 		
 		selector.setCurrentPopulation(population);
 		while(nextGen.size() < popSize){
@@ -62,6 +72,7 @@ public class GeneticAlgo<I extends GAIndividual> {
 			}
 			nextGen.addAll(freshInds);
 		}
+		
 		if(popSize % 2 == 1){
 			Random rnd = new Random();
 			nextGen.remove(rnd.nextInt(popSize));

+ 194 - 0
src/algorithms/geneticAlgorithm/Components/Selections/TournamentProportionalSelection.java

@@ -0,0 +1,194 @@
+package algorithms.geneticAlgorithm.Components.Selections;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Random;
+
+import algorithms.geneticAlgorithm.Components.GAIndividual;
+import algorithms.geneticAlgorithm.Components.GASelectionStrategy;
+
+public class TournamentProportionalSelection<I extends GAIndividual> implements GASelectionStrategy<I>{
+
+	public class Range{
+		
+		public double min;
+		public double max;
+		public Range(double min, double max){
+			this.min = min;
+			this.max = max;
+		}
+	}
+	
+	private ArrayList<I> currentPop;
+	public int tournamentSize;
+	private Random rng; 
+	private ArrayList<Range> tournamentWheel;
+	public ArrayList<I> competitors;
+	//public double selectProb;
+	private double maxRange;
+	
+	
+	public TournamentProportionalSelection(){
+		currentPop = new ArrayList<I>();
+		tournamentSize = 1;
+		rng = new Random();
+	}
+	
+	public TournamentProportionalSelection(int tSize){
+		currentPop = new ArrayList<I>();
+		rng = new Random();
+		tournamentSize = tSize;
+	}
+	
+	@Override
+	public void setCurrentPopulation(ArrayList<I> population) {
+		currentPop.clear();
+		currentPop.addAll(population);
+	}
+	
+	public void setTournamentSize(int size){
+		if(size <= 0){
+			tournamentSize = 1;
+		}else{
+			tournamentSize = size;
+		}
+	}
+
+	@Override
+	public ArrayList<I> selectIndividuals() {
+		ArrayList<I> parents = new ArrayList<I>();
+		parents.add(selectSingleIndividual());
+		parents.add(selectSingleIndividual());
+		return parents;
+	}
+	
+	public I selectSingleIndividual(){
+		tournamentSelection();
+		if(competitors.get(competitors.size()-1).getFittness() <= 0){
+			normalizedWheelInit();
+		}else{
+			proportionalWheelInit();
+		}
+		//initWheel();
+		double index = rng.nextDouble() * maxRange;
+		for(int i = 0; i < tournamentWheel.size(); i++){
+			if(index >= tournamentWheel.get(i).min && index <= tournamentWheel.get(i).max){
+				return competitors.get(i);
+			}
+		}
+		return competitors.get(rng.nextInt(competitors.size()));
+	}
+	
+	public void tournamentSelection(){
+		competitors = new ArrayList<I>();
+		Collections.shuffle(currentPop);
+		for(int i = 0; i < tournamentSize; i++){
+			I candidate = currentPop.get(i);
+			int size = competitors.size();
+			for(int j = 0; j <= size; j++){
+				if(j != size){
+					if(competitors.get(j).getFittness() < candidate.getFittness()){
+						competitors.add(j, candidate);
+						break;
+					}
+				}else{
+					competitors.add(candidate);
+				}
+			}
+		}		
+	}
+	
+	public I chooseCandidate(){
+		int index = rng.nextInt(currentPop.size());
+		I candidate = currentPop.get(index);
+		return candidate;
+	}
+	
+	public void initWheel(){
+		tournamentWheel = new ArrayList<Range>();
+		maxRange = 0;
+		double smallestFittness = competitors.get(competitors.size()).getFittness();
+		double biggestFittness = competitors.get(0).getFittness();
+		double distance = biggestFittness - smallestFittness;
+		double fittnessSum = 0;
+		for(GAIndividual i : competitors){
+			fittnessSum += i.getFittness();
+		}
+		if(smallestFittness <= 0){
+			smallestFittness = 0 - smallestFittness;
+		}
+		fittnessSum += competitors.size() * smallestFittness;
+		double avgFittness = fittnessSum / competitors.size();
+		double relativeSizeFactor = 1;
+		if(distance != 0){
+			relativeSizeFactor = distance/avgFittness;
+		}
+		double addedValue = (fittnessSum / relativeSizeFactor) * (1/competitors.size());
+		fittnessSum += competitors.size() * addedValue;
+		
+		for(GAIndividual i : competitors){
+			
+			Range range = new Range(maxRange, maxRange + i.getFittness() + smallestFittness + addedValue);
+			tournamentWheel.add(range);
+			maxRange += maxRange + i.getFittness() + smallestFittness + addedValue;
+			i.addLogEntry("Selection Prob: " + 
+					(fittnessSum/(i.getFittness()+smallestFittness+addedValue))*100 + "%");
+		}
+	}
+	
+	public void normalizedWheelInit(){
+		tournamentWheel = new ArrayList<Range>();
+		maxRange = 0;
+		double smallestFittness = competitors.get(competitors.size()-1).getFittness();
+		double biggestFittness = competitors.get(0).getFittness();
+		//System.out.println("smallest: " + smallestFittness);
+		//System.out.println("biggest: " + biggestFittness);
+		double distance = biggestFittness - smallestFittness;
+		//System.out.println("distance: " + distance);
+		smallestFittness = Math.abs(smallestFittness);
+		biggestFittness = Math.abs(smallestFittness);
+
+		double fittnessSum = 0;
+		for(GAIndividual i : competitors){
+			fittnessSum += i.getFittness();
+		}
+		fittnessSum += (smallestFittness)*competitors.size();
+		double relativeMaxSizeFactor = 1;
+		double relativeMinSizeFactor = 1;
+		
+		if(distance > 0){
+			relativeMaxSizeFactor = distance/biggestFittness;
+			if(smallestFittness > 0){
+				relativeMinSizeFactor = distance/smallestFittness;
+			}
+		}
+		
+		double avgRelativeSizeFactor = relativeMaxSizeFactor + relativeMinSizeFactor;
+		avgRelativeSizeFactor = avgRelativeSizeFactor/2;
+		double addedValue = fittnessSum / avgRelativeSizeFactor;
+		fittnessSum += addedValue;
+		addedValue = addedValue/competitors.size();
+		maxRange = 0;
+		for(GAIndividual i : competitors){
+			double rangeEnd = maxRange + i.getFittness() + smallestFittness + addedValue;
+			Range range = new Range(maxRange, rangeEnd);
+			i.addLogEntry("Selection Prob : " + ((rangeEnd - maxRange)/fittnessSum)*100
+					+ "%");
+			maxRange = rangeEnd;	
+		}
+		
+	}
+	
+	public void proportionalWheelInit(){
+		tournamentWheel = new ArrayList<Range>();
+		maxRange = 0;
+		for(GAIndividual i : competitors){
+			
+			Range range = new Range(maxRange, maxRange + i.getFittness());
+			maxRange += maxRange + i.getFittness();
+			i.addLogEntry("proportional Selection");
+		}
+	}
+
+}
+

+ 6 - 2
src/algorithms/geneticAlgorithm/Components/Selections/TournamentRankSelection.java

@@ -1,6 +1,7 @@
 package algorithms.geneticAlgorithm.Components.Selections;
 
 import java.util.ArrayList;
+import java.util.Collections;
 import java.util.Random;
 
 import algorithms.geneticAlgorithm.Components.GAIndividual;
@@ -41,7 +42,8 @@ public class TournamentRankSelection<I extends GAIndividual> implements GASelect
 	
 	@Override
 	public void setCurrentPopulation(ArrayList<I> population) {
-		currentPop = population;
+		currentPop.clear();
+		currentPop.addAll(population);
 	}
 	
 	public void setTournamentSize(int size){
@@ -70,8 +72,10 @@ public class TournamentRankSelection<I extends GAIndividual> implements GASelect
 	
 	public void tournamentSelection(){
 		competitors = new ArrayList<I>();
+		Collections.shuffle(currentPop);
 		for(int i = 0; i < tournamentSize; i++){
-			I candidate = chooseCandidate();
+			//I candidate = chooseCandidate();
+			I candidate = currentPop.get(i);
 			int size = competitors.size();
 			for(int j = 0; j <= size; j++){
 				if(j != size){

+ 40 - 0
src/algorithms/geneticAlgorithm/holegGA/Components/AlgoRunnable.java

@@ -0,0 +1,40 @@
+package algorithms.geneticAlgorithm.holegGA.Components;
+
+import java.util.ArrayList;
+
+import algorithms.geneticAlgorithm.Components.GACrossoverStrategy;
+import algorithms.geneticAlgorithm.Components.GAFittnessFunctionStrategy;
+import algorithms.geneticAlgorithm.Components.GAIndividual;
+import algorithms.geneticAlgorithm.Components.GAMutationStrategy;
+import algorithms.geneticAlgorithm.Components.GASelectionStrategy;
+
+public class AlgoRunnable implements Runnable {
+	GASelectionStrategy selection;
+	GACrossoverStrategy crossover;
+	GAMutationStrategy mutation;
+	GAFittnessFunctionStrategy fittness;
+	ArrayList<GAIndividual> individuals;
+	ArrayList<GAIndividual> nextGen;
+	
+	public AlgoRunnable(GASelectionStrategy selection, GACrossoverStrategy crossover, 
+			GAMutationStrategy mutation, GAFittnessFunctionStrategy fittness, ArrayList<GAIndividual> individuals, ArrayList<GAIndividual> nextGen){
+		this.selection = selection;
+		this.crossover = crossover;
+		this.mutation = mutation;
+		this.fittness = fittness;
+		this.individuals = individuals;
+		this.nextGen = nextGen;
+		
+	}
+
+	@Override
+	public void run() {
+		individuals = crossover.crossOver(individuals);
+		for(GAIndividual individual : individuals){
+			individual = mutation.mutateIndividual(individual);
+			fittness.calculateFittness(individual);
+		}
+		nextGen.addAll(individuals);	
+	}
+
+}

+ 43 - 66
src/algorithms/geneticAlgorithm/holegGA/Components/HolegCrossover.java

@@ -19,102 +19,79 @@ public class HolegCrossover extends GACrossoverStrategy<HolegIndividual> {
 	}
 
 	private HolegIndividual createChild(HolegIndividual parent1, HolegIndividual parent2) {
-		HolegIndividual child = new HolegIndividual(parent1.getOriginObjects());
+		HolegIndividual child = new HolegIndividual(parent1.getOriginObjects(), null);
 		ArrayList<HolegIndividual> parents = new ArrayList<HolegIndividual>();
 		parents.add(parent1);
 		parents.add(parent2);
 		child.setParents(parents);
 		
-		ArrayList<Integer> parent1NonOrgIndexes = parent1.getNonOriginIndexes();
-		int splitIdx = (int) Math.ceil((double)parent1NonOrgIndexes.size()/2);
+		ArrayList<Integer> parent1WildCardIndexes = parent1.wildCardIndexes;
+		int splitIdx = (int) Math.ceil((double)parent1WildCardIndexes.size()/2);
 		
-		//HolonObjects
 		for(int i = 0; i < splitIdx; i++){
-			int index = parent1NonOrgIndexes.get(i);
+			int index = parent1WildCardIndexes.get(i);
 			
-			child.addObjectWithIdx(parent1.indexToObjectMap.get(index).makeCopy(), index);
+			AbstractCpsObject wildObj = parent1.indexToObjectMap.get(index);
+			AbstractCpsObject newWildObj = wildObj.makeCopy();
+			newWildObj.setId(wildObj.getId());
+			newWildObj.setPosition(wildObj.getPosition());
+			child.addObject(newWildObj);
 		}
-		int restAmount = parent1NonOrgIndexes.size() - splitIdx;
+		int restAmount = parent1WildCardIndexes.size() - splitIdx;
 		
-		ArrayList<Integer> parent2NonOrgIndexes = parent2.getNonOriginIndexes();
+		ArrayList<Integer> parent2WildCardIndexes = parent2.wildCardIndexes;
 		for(int j = 0; j < restAmount; j++){
-			int index = parent2NonOrgIndexes.size() - 1; //greift auf letztes element zu
+			int index = parent2WildCardIndexes.size() - 1; //greift auf letztes element zu
 			index -= j;	//greift bei jedem durchlauf auf ein weiter vorderes element zu
 			if(index >= 0){
-				int objIdx = parent2NonOrgIndexes.get(index);
-				child.addObjectWithIdx(parent2.indexToObjectMap.get(objIdx).makeCopy(), objIdx);
+				int objIdx = parent2WildCardIndexes.get(index);
+				
+				AbstractCpsObject wildObj = parent2.indexToObjectMap.get(objIdx);
+				AbstractCpsObject newWildObj = wildObj.makeCopy();
+				newWildObj.setId(wildObj.getId());
+				newWildObj.setPosition(wildObj.getPosition());
+				child.addObject(newWildObj);
 			}else{
 				break;
 			}
 		}
 		
+		child.wildCardIndexes = parent1.wildCardIndexes;
+		
+		//OriginEdges
+		splitIdx = (int) Math.ceil((double)parent1.getOriginalEdges().size()/2);
+		for(int i = 0; i < splitIdx; i++){
+			child.addOriginalEdge(parent1.getOriginalEdges().get(i));
+		}
+		
+		restAmount = parent1.getOriginalEdges().size() - splitIdx;
+		for(int j = 0; j < restAmount; j++){
+			int idx = parent2.getOriginalEdges().size() - 1;
+			idx -= j;
+			if(idx >= 0){
+				child.addOriginalEdge(parent2.getOriginalEdges().get(idx));
+			}
+		}
+		
 		//HolonEdges
-		splitIdx = (int) Math.ceil((double)parent1.getEdges().size()/2);
+		splitIdx = (int) Math.ceil((double)parent1.getAdditionalEdges().size()/2);
 		for(int k = 0; k < splitIdx; k++){
-			int posA = parent1.getEdges().get(k).aPos;
-			int posB = parent1.getEdges().get(k).bPos;
+			int posA = parent1.getAdditionalEdges().get(k).aPos;
+			int posB = parent1.getAdditionalEdges().get(k).bPos;
 			
 			child.addEdge(posA, posB);
-			
-			/*
-			AbstractCpsObject objA;
-			AbstractCpsObject objB;
-			
-			if(posA < child.holonObjects.size()){
-				objA = child.holonObjects.get(posA);
-				if(objA == null){
-					objA = new CpsNode("Node");
-					child.holonObjects.set(posA, objA);
-				}
-			}else{
-				objA = new CpsNode("Node");
-				child.holonObjects.add(objA);
-			}
-			
-			if(posB < child.holonObjects.size()){
-				objB = child.holonObjects.get(posB);
-				if(objB == null){
-					objB =  new CpsNode("Node");
-					child.holonObjects.set(posB, objB);
-				}
-			}else{
-				objB = new CpsNode("Node");
-				child.holonObjects.add(objB);
-			}
-			child.holonEdges.add(new GAEdge(posA, posB, objA, objB));
-			*/
 		}
 		
-		restAmount = parent1.getEdges().size() - splitIdx;
+		restAmount = parent1.getAdditionalEdges().size() - splitIdx;
 		for(int l = 0; l < restAmount; l++){
-			int idx = parent2.getEdges().size() - 1;
+			int idx = parent2.getAdditionalEdges().size() - 1;
 			idx -= l;
 			
 			if(idx >= 0){
-				int posA = parent2.getEdges().get(idx).aPos;
-				int posB = parent2.getEdges().get(idx).bPos;
+				int posA = parent2.getAdditionalEdges().get(idx).aPos;
+				int posB = parent2.getAdditionalEdges().get(idx).bPos;
 				
 				child.addEdge(posA, posB);
-				
-				/*
-				AbstractCpsObject objA;
-				AbstractCpsObject objB;
-			
-				if(posA < child.holonObjects.size()){
-					objA = child.holonObjects.get(posA);
-				}else{
-					objA = new CpsNode("Node");
-					child.holonObjects.add(objA); /// muss unbedingt geändert werden damit edges synchron sind
-				}
-			
-				if(posB < child.holonObjects.size()){
-					objB = child.holonObjects.get(posB);
-				}else{
-					objB = new CpsNode("Node");
-					child.holonObjects.add(objB);
-				}
-				child.holonEdges.add(new GAEdge(posA, posB, objA, objB));
-				*/
 			}
 		}
 		return child;

+ 57 - 11
src/algorithms/geneticAlgorithm/holegGA/Components/HolegFactory.java

@@ -1,5 +1,6 @@
 package algorithms.geneticAlgorithm.holegGA.Components;
 
+import java.lang.reflect.Array;
 import java.lang.reflect.Constructor;
 import java.lang.reflect.InvocationTargetException;
 import java.util.ArrayList;
@@ -7,52 +8,92 @@ import java.util.Collections;
 import java.util.Random;
 
 import classes.AbstractCpsObject;
+import classes.CpsEdge;
 import classes.CpsNode;
 import classes.HolonBattery;
 import classes.HolonObject;
 import classes.HolonSwitch;
+import classes.HolonWildCard;
 import algorithms.geneticAlgorithm.Components.GAIndividualFactory;
+import algorithms.geneticAlgorithm.holegGA.GAEdge;
 
 public class HolegFactory implements GAIndividualFactory<HolegIndividual> {
 
 	ArrayList<AbstractCpsObject> objectSpace;
-	public ArrayList<AbstractCpsObject> originObjects;
+	public ArrayList<AbstractCpsObject> originalObjects;
+	public ArrayList<CpsEdge> originalEdges;
 	public int maxObjects;
 	public int maxConnections;
 	Random rng;
-	public boolean onlyNodes;
+	public boolean editEdges;
 	
 	public HolegFactory(ArrayList<AbstractCpsObject> objects, int maxObjects, int maxConnections){
 		objectSpace = objects;
-		objectSpace.add(null);
 		this.maxObjects = maxObjects;
 		this.maxConnections = maxConnections;
 		rng = new Random();
-		originObjects = new ArrayList<AbstractCpsObject>();
-		onlyNodes = false;
+		originalObjects = new ArrayList<AbstractCpsObject>();
+		originalEdges = new ArrayList<CpsEdge>();
+		editEdges = false;
 	}
 	
 	@Override
 	public HolegIndividual createRandomIndividual() {
-		HolegIndividual hI = new HolegIndividual(originObjects);
+		HolegIndividual hI = new HolegIndividual(originalObjects, originalEdges);
+		
+		/*
 		if(maxObjects > 0){
 			createObjects(hI);
 		}
+		*/
+		setWildCards(hI);
+		if(editEdges){
+			editEdges(hI);
+		}
 		if(maxConnections > 0){
 			createEdges(hI);
 		}
 		return hI;
 	}
+
+	private void setWildCards(HolegIndividual hI) {
+		int setAmount = rng.nextInt(hI.getWildcardIndexes().size() + 1);
+		ArrayList<Integer> list = new ArrayList<Integer>();
+		list.addAll(hI.getWildcardIndexes());
+		Collections.shuffle(list);
+		int spaceIdx = 0;
+		if(objectSpace.size() > 0){
+			for(int i = 0; i < setAmount; i++){
+				AbstractCpsObject wildCard = hI.indexToObjectMap.get(list.get(i));
+				spaceIdx = rng.nextInt(objectSpace.size());
+				AbstractCpsObject newObj = objectSpace.get(spaceIdx).makeCopy();
+				newObj.setPosition(wildCard.getPosition());
+				newObj.setId(wildCard.getId());
+				hI.addObjectWithIdx(newObj, newObj.getId());
+			}
+		}
+	}
 	
+	private void editEdges(HolegIndividual hI) {
+		if(hI.getOriginalEdges().size() > 0 && hI.getIndexes().size() > 2){
+			int editAmount = rng.nextInt(hI.getOriginalEdges().size());
+			for(int i = 0; i < editAmount; i++){
+				int edgeIdx = rng.nextInt(hI.getOriginalEdges().size());
+				GAEdge toChange = hI.getOriginalEdges().get(edgeIdx);
+				HolegMutation.changeSingleEdge(hI, toChange, true);
+			}
+		}
+	}
+
 	public void createObjects(HolegIndividual hI){
-		
+	
 		int objCount = rng.nextInt(maxObjects) + 1;
 		
 		for(int i = 0; i < objCount; i++){
 			
 			
 			AbstractCpsObject newObj = null;
-			if(!onlyNodes){
+			if(!editEdges){
 				AbstractCpsObject absObj = objectSpace.get(rng.nextInt(objectSpace.size()));
 				if(absObj instanceof HolonObject){
 					newObj = new HolonObject(absObj);
@@ -60,6 +101,8 @@ public class HolegFactory implements GAIndividualFactory<HolegIndividual> {
 					newObj = new HolonSwitch(absObj);
 				}else if(absObj instanceof HolonBattery){
 					newObj = new HolonBattery(absObj);
+				}else if(absObj instanceof HolonWildCard){
+					newObj = new HolonWildCard(absObj);
 				}else if(absObj == null){
 					newObj = new CpsNode("Node");
 				}
@@ -74,19 +117,22 @@ public class HolegFactory implements GAIndividualFactory<HolegIndividual> {
 	
 	public void createEdges(HolegIndividual hI){
 		if(hI.getIndexes().size() > 1){
-			int edgeCount = rng.nextInt(maxConnections) + 1;
+			int edgeCount = rng.nextInt(maxConnections + 1);
 			ArrayList<Integer> list = new ArrayList<Integer>();
 	    
 			for (int i = 0; i < hI.getIndexes().size(); i++) {
 				list.add(hI.getIndexes().get(i));
 			}
 	   
-		
+			if(edgeCount >= hI.getAllEdges().size()){
+				edgeCount -= hI.getAllEdges().size();
+			}else{
+				edgeCount = 0;
+			}
 			for(int i = 0; i < edgeCount; i++){
 				Collections.shuffle(list);
 				int aPos = list.get(0);
 				int bPos = list.get(1);
-				//hI.holonEdges.add(new GAEdge(aPos, bPos, hI.holonObjects.get(aPos), hI.holonObjects.get(bPos)));
 				hI.addEdge(aPos, bPos);
 			}
 		}

+ 43 - 18
src/algorithms/geneticAlgorithm/holegGA/Components/HolegFittnessFkt.java

@@ -1,25 +1,27 @@
 package algorithms.geneticAlgorithm.holegGA.Components;
 
-import java.util.ArrayList;
-
 import ui.controller.Control;
 import ui.controller.SimulationManager;
 import ui.model.Model;
 import classes.AbstractCpsObject;
 import classes.HolonObject;
+import classes.SubNet;
 import algorithms.geneticAlgorithm.Components.GAFittnessFunctionStrategy;
-import algorithms.geneticAlgorithm.Components.GAIndividual;
+import algorithms.geneticAlgorithm.holegGA.ParameterArray;
 
 public class HolegFittnessFkt implements GAFittnessFunctionStrategy<HolegIndividual>{
 	
 	Control controller;
 	Model model;
 	SimulationManager simManager;
+	ParameterArray params;
+	double suppliedPoints;
+	double oversuppliedPoints;
+	double undersuppliedPoints;
+	double partiallysuppliedPoints;
+	boolean everyoneSupplied;
 	
 	public HolegFittnessFkt(Control controller){
-		//this.controller = controller;
-		//model = controller.getModel();
-		//simManager = controller.getSimManager();
 		model = new Model();
 		simManager = new SimulationManager(model);
 	}
@@ -28,10 +30,12 @@ public class HolegFittnessFkt implements GAFittnessFunctionStrategy<HolegIndivid
 	public double calculateFittness(HolegIndividual candidate){
 		model.getObjectsOnCanvas().clear();
 		model.getEdgesOnCanvas().clear();
+		candidate.configurateNetwork();
 		model.getObjectsOnCanvas().addAll(candidate.getObjects());
-		model.getEdgesOnCanvas().addAll(candidate.getEdges());
+		model.getEdgesOnCanvas().addAll(candidate.getAllEdges());
 		simManager.calculateStateForTimeStep(model.getCurIteration());
 		
+		everyoneSupplied = true;
 		double fittness = 0;
 		for(AbstractCpsObject abs : candidate.getObjects()){
 			if(abs instanceof HolonObject){
@@ -39,29 +43,50 @@ public class HolegFittnessFkt implements GAFittnessFunctionStrategy<HolegIndivid
 				switch (((HolonObject) abs).getState()){
 					
 				case HolonObject.SUPPLIED : 
-					fittness += 10;
+					fittness += suppliedPoints;
+					break;
+				
+				case HolonObject.OVER_SUPPLIED :
+					fittness += oversuppliedPoints;
+					everyoneSupplied = false;
 					break;
 						
 				case HolonObject.NOT_SUPPLIED :
-					fittness -= 5;
+					fittness += undersuppliedPoints;
+					everyoneSupplied = false;
+					break;
+				case HolonObject.PARTIALLY_SUPPLIED:
+					fittness += partiallysuppliedPoints;
+					everyoneSupplied = false;
 					break;
-					
-				}
-				/*
-				if(((HolonObject) abs).getState() == HolonObject.SUPPLIED){
-					fittness += 100;
 				}
-				*/
 			}
 		}
-		fittness -= candidate.getEdges().size()*0.1;
-		candidate.setFittness(fittness);
-		//candidate.addLogEntry("Fittness: " + fittness);
 		return fittness;
 	}
 	
+	public float getCurrentOverProduction(){
+		float overProd = 0;
+		for(SubNet subnet : simManager.getSubNets()){
+			overProd += subnet.spareProduction;
+		}
+		return overProd;
+	}
+	
+	public boolean getEveryoneSupplied(){
+		return everyoneSupplied;
+	}
+	
 	public Model getModel(){
 		return model;
 	}
+	
+	public void setParameters(ParameterArray params){
+		this.params = params;
+		suppliedPoints = (double)params.get(params.SUPPLIED_POINTS);
+		oversuppliedPoints = (double)params.get(params.OVERSUPPLIED_POINTS);
+		undersuppliedPoints = (double)params.get(params.UNDERSUPPLIED_POINTS);
+		partiallysuppliedPoints = (double)params.get(params.PARTIALSUPPLIED_POINTS);
+	}
 		
 }

+ 186 - 5
src/algorithms/geneticAlgorithm/holegGA/Components/HolegFittnessScenario.java

@@ -1,9 +1,20 @@
 package algorithms.geneticAlgorithm.holegGA.Components;
 
+import java.math.BigDecimal;
+import java.math.RoundingMode;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Random;
+
+import classes.CpsEdge;
+import classes.HolonWildCard;
+import classes.Position;
 import ui.controller.Control;
 import ui.controller.SimulationManager;
 import ui.model.Model;
 import algorithms.geneticAlgorithm.Components.GAFittnessFunctionStrategy;
+import algorithms.geneticAlgorithm.holegGA.GAEdge;
+import algorithms.geneticAlgorithm.holegGA.ParameterArray;
 
 public class HolegFittnessScenario implements GAFittnessFunctionStrategy<HolegIndividual>{
 
@@ -11,6 +22,18 @@ public class HolegFittnessScenario implements GAFittnessFunctionStrategy<HolegIn
 	Control controller;
 	Model model;
 	SimulationManager simManager;
+	ParameterArray params;
+	int edgeBreakCount;
+	double edgeLengthPoints;
+	double wildcardPoints;
+	double overprodPoints;
+	int totalSteps = 100;
+	int singleStep;
+	int breakCounter = 0;
+	HolegIndividual originalNetwork;
+	ArrayList<Integer> edgeBreakingIndexes = new ArrayList<Integer>();
+	double globalOverProd;
+	Random rng = new Random();
 		
 	public HolegFittnessScenario(Control controller) {
 		singleFkt = new HolegFittnessFkt(controller);
@@ -20,16 +43,174 @@ public class HolegFittnessScenario implements GAFittnessFunctionStrategy<HolegIn
 	
 	@Override
 	public double calculateFittness(HolegIndividual candidate) {
+		globalOverProd = 0;
+		double fittness = 0;
+		double noBreakFittness = calcFittnessWithoutBreak(candidate);
+		fittness += noBreakFittness;
+		candidate.addLogEntry("Fittness without break: " + noBreakFittness);
+		double breakFittness = calcFittnessWithBreak(candidate);
+		candidate.addLogEntry("Fittness with break: " + breakFittness);
+		fittness += breakFittness;
+		fittness = fittness /2;
+		globalOverProd = globalOverProd / 2;
+		globalOverProd = globalOverProd / totalSteps;
+		
+		for(Integer wildIdx : candidate.getWildcardIndexes()){
+			if(!(candidate.indexToObjectMap.get(wildIdx) instanceof HolonWildCard)){
+				fittness += wildcardPoints;
+			}
+		}
+		
+		double edgeLength = 0;
+		for(GAEdge e : candidate.getAllEdges()){
+			Position aPos = e.getA().getPosition();
+			Position bPos = e.getB().getPosition();
+			double xDiff = Math.abs(aPos.x - bPos.x);
+			double yDiff = Math.abs(aPos.y - bPos.y);
+			edgeLength += Math.sqrt(Math.pow(xDiff, 2) + Math.pow(yDiff, 2));
+		}
+		
+		candidate.setEdgeLength(getRoundedValue(edgeLength));
+		candidate.addLogEntry("Total Edge Length: " + getRoundedValue(edgeLength));
+		fittness += (edgeLength/100)*edgeLengthPoints;
+		
+		candidate.addLogEntry("average Overproduction: " + getRoundedValue(globalOverProd));
+		
+		candidate.setFittness(getRoundedValue(fittness));		
+		candidate.addLogEntry("Fittness: " + getRoundedValue(fittness));
+		return fittness;
+	}
+	
+	public double calcFittnessWithoutBreak(HolegIndividual candidate){
+		double fittness = 0;
+		double avgOverProduction = 0;
+		
+		for(CpsEdge edge : candidate.brokenEdges){
+			edge.setWorkingState(true);
+		}
+		candidate.brokenEdges.clear();
+		
+		for(int i = 0; i < totalSteps; i++){
+			model.setCurIteration(singleStep * i);
+			fittness += singleFkt.calculateFittness(candidate);
+			avgOverProduction += singleFkt.getCurrentOverProduction();
+		}
+		
+		globalOverProd += avgOverProduction;
+		fittness += (avgOverProduction / 1000) * overprodPoints;
+		fittness = (int)fittness;
+		fittness = fittness/totalSteps;
+		return fittness;
+	}
+	
+	public double calcFittnessWithBreak(HolegIndividual candidate){
 		double fittness = 0;
-		for(int i = 0; i < 100; i++){
-			model.setCurIteration(i);
+		double avgOverProduction = 0;
+		
+		for(CpsEdge edge : candidate.brokenEdges){
+			edge.setWorkingState(true);
+		}
+
+		breakEdges(candidate);
+		
+		for(int i = 0; i < totalSteps; i++){
+			model.setCurIteration(singleStep * i);
 			fittness += singleFkt.calculateFittness(candidate);
+			avgOverProduction += singleFkt.getCurrentOverProduction();
 		}
+		
+		globalOverProd += avgOverProduction;
+		fittness += (avgOverProduction / 1000) * overprodPoints;
 		fittness = (int)fittness;
-		fittness =	fittness * 0.01;
-		candidate.setFittness(fittness);
-		candidate.addLogEntry("Fittness: " + fittness);
+		fittness = fittness/totalSteps;
+
 		return fittness;
 	}
+	
+	private void breakEdges(HolegIndividual candidate) {
+		candidate.brokenEdges.clear();
+		int unbrokenEdges = 0;
+		for(Integer idx : edgeBreakingIndexes){
+			ArrayList<CpsEdge> healthyEdges = new ArrayList<CpsEdge>();
+			
+			
+			for(CpsEdge edge : candidate.indexToObjectMap.get(idx).getConnections()){
+				if(edge.isWorking()){
+					healthyEdges.add(edge);
+				}
+			}
+		
+			Collections.shuffle(healthyEdges);
+			if(healthyEdges.size() > 0){
+				healthyEdges.get(0).setWorkingState(false);
+				candidate.brokenEdges.add(healthyEdges.get(0));
+			}else{
+				unbrokenEdges++;
+			}
+		}
+		if(unbrokenEdges > 0){
+			ArrayList<CpsEdge> healthyEdges = new ArrayList<CpsEdge>();
+			for(CpsEdge edge : candidate.getAllEdges()){
+				if(edge.isWorking()){
+					healthyEdges.add(edge);
+				}
+			}
+			Collections.shuffle(healthyEdges);
+			int bound;
+			if(unbrokenEdges <= healthyEdges.size()){
+				bound = unbrokenEdges;
+			}else{
+				bound = healthyEdges.size();
+			}
+			for(int i = 0; i < bound; i++){
+				healthyEdges.get(i).setWorkingState(false);
+			}
+		}
+		
+	}
 
+	public void setParameters(ParameterArray params){
+		this.params = params;
+		edgeBreakCount = (int)params.get(params.EDGE_BREAK_AMOUNT);
+		edgeLengthPoints = (double)params.get(params.LENGTH_POINTS);
+		wildcardPoints = (double)params.get(params.WILDCARD_USAGE);
+		totalSteps = (int)params.get(params.SIM_ITERATIONS);
+		overprodPoints = (double)params.get(params.OVERPRODUCTION);
+		originalNetwork = (HolegIndividual)params.get(params.ORIGINAL_NETWORK);
+		if(totalSteps < 100){
+			singleStep = (int) Math.floor(100/totalSteps);
+		}else{
+			singleStep = 1;
+		}
+		
+		singleFkt.setParameters(params);
+	}
+	
+	/*
+	 * method is called before a new generation is calculated
+	 * setting the specific edge breaks here
+	 */
+	public void initialize(){
+		edgeBreakingIndexes.clear();
+		ArrayList<Integer> objIndexes = new ArrayList<Integer>();
+		objIndexes.addAll(originalNetwork.getIndexes());
+		Collections.shuffle(objIndexes);
+		//shuffeling leads to random selection of Indexes
+		int bound;
+		if(edgeBreakCount <= objIndexes.size()){
+			bound = edgeBreakCount;
+		}else{
+			bound = objIndexes.size();
+		}
+		for(int i = 0; i < bound; i++){
+			//edgeBreakingIndexes.add(objIndexes.get(i));
+			edgeBreakingIndexes.add(objIndexes.get(rng.nextInt(objIndexes.size())));
+		}
+	}
+
+	public double getRoundedValue(double value){
+		BigDecimal bd = new BigDecimal(value);
+		bd = bd.setScale(2, RoundingMode.HALF_UP);
+		return bd.doubleValue();
+	}
 }

+ 4 - 1
src/algorithms/geneticAlgorithm/holegGA/Components/HolegGeneration.java

@@ -4,6 +4,8 @@ import java.util.ArrayList;
 
 public class HolegGeneration {
 	
+	public static int ORIGINAL_GEN = -1;
+	
 	ArrayList<HolegIndividual> generation;
 	int genCount;
 	String name;
@@ -39,7 +41,7 @@ public class HolegGeneration {
 	}
 	
 	public String getInformation(){
-		log = "";
+		log = "Generation Log";
 		if(generation.size() > 0){
 			addLogEntry("Avg Fittness: " + getAvgFittness());
 			addLogEntry("Max Fittness: " + getMaxFittness());
@@ -53,6 +55,7 @@ public class HolegGeneration {
 		for(HolegIndividual i : generation){
 			fittness += i.getFittness();
 		}
+		
 		return (fittness/generation.size());
 	}
 	

+ 96 - 33
src/algorithms/geneticAlgorithm/holegGA/Components/HolegIndividual.java

@@ -5,47 +5,64 @@ import java.util.HashMap;
 import java.util.Set;
 
 import classes.AbstractCpsObject;
+import classes.CpsEdge;
 import classes.CpsNode;
+import classes.HolonWildCard;
 import algorithms.geneticAlgorithm.Components.GAIndividual;
 import algorithms.geneticAlgorithm.holegGA.GAEdge;
 
 public class HolegIndividual extends GAIndividual {
 	
-	private ArrayList<GAEdge> holonEdges;
-	public ArrayList<Integer> indexes;
-	public ArrayList<Integer> originIndexes;
-	public ArrayList<HolegIndividual> parents;
-	public HashMap<Integer, AbstractCpsObject> indexToObjectMap;
-	private HashMap<AbstractCpsObject, Integer> objectToIndexMap;
+	public ArrayList<CpsEdge> brokenEdges = new ArrayList<CpsEdge>();
+	public ArrayList<GAEdge> additionalEdges = new ArrayList<GAEdge>();
+	public ArrayList<GAEdge> originEdges = new ArrayList<GAEdge>();
+	public ArrayList<Integer> indexes = new ArrayList<Integer>();
+	public ArrayList<Integer> originIndexes = new ArrayList<Integer>();
+	public ArrayList<Integer> wildCardIndexes = new ArrayList<Integer>();
+	public ArrayList<HolegIndividual> parents = new ArrayList<HolegIndividual>();
+	public HashMap<Integer, AbstractCpsObject> indexToObjectMap = new HashMap<Integer, AbstractCpsObject>();
+	private HashMap<AbstractCpsObject, Integer> objectToIndexMap = new HashMap<AbstractCpsObject, Integer>();
 	public boolean drawn;
 	public String id;
 	public String log;
+	public String backupLog = "Individual Log";
 	public int gen;
 	public int pos;
 	private int lastIndex;
+	public double totalEdgeLength;
 	
-	public HolegIndividual(ArrayList<AbstractCpsObject> originObjects){
-		holonEdges = new ArrayList<GAEdge>();
-		indexes = new ArrayList<Integer>();
-		originIndexes = new ArrayList<Integer>();
-		parents = new ArrayList<HolegIndividual>();
-		indexToObjectMap = new HashMap<Integer, AbstractCpsObject>();
-		objectToIndexMap = new HashMap<AbstractCpsObject, Integer>();
+	public HolegIndividual(ArrayList<AbstractCpsObject> originObjects, 
+			ArrayList<CpsEdge> originalEdges){
+
 		lastIndex = 0;
 		log = "Individual Log";
 		drawn = false;
 		
 		for(AbstractCpsObject abs : originObjects){
+
 			AbstractCpsObject newObj = abs.makeCopy();
 			newObj.setPosition(abs.getPosition());
+			newObj.setId(abs.getId());
 			addObject(newObj);
 			originIndexes.add(objectToIndexMap.get(newObj));
+			if(newObj instanceof HolonWildCard){
+				wildCardIndexes.add(objectToIndexMap.get(newObj));
+			}
+			
+		}
+		
+		if(originalEdges != null){
+			for(CpsEdge e : originalEdges){
+				addOriginalEdge(e);
+			}
 		}
 	}
 	
 	public HolegIndividual(HolegIndividual indi){
-		holonEdges = new ArrayList<GAEdge>();
-		holonEdges.addAll(indi.getEdges());
+		additionalEdges = new ArrayList<GAEdge>();
+		additionalEdges.addAll(indi.getAdditionalEdges());
+		originEdges = new ArrayList<GAEdge>();
+		originEdges.addAll(indi.originEdges);
 		indexes = new ArrayList<Integer>();
 		indexes.addAll(indi.getIndexes());
 		originIndexes = new ArrayList<Integer>();
@@ -75,6 +92,7 @@ public class HolegIndividual extends GAIndividual {
 		for(int i = 0; i < parents.size(); i++){
 			addLogEntry("Parent" + i + ": " + parents.get(i).getId());
 		}
+		backupLog = log;
 	}
 	
 	public void setId(int Gen, int pos){
@@ -117,21 +135,31 @@ public class HolegIndividual extends GAIndividual {
 		return indexes;
 	}
 	
-	public ArrayList<Integer> getNonOriginIndexes(){
-		if(indexes.size() > originIndexes.size()){
-			return new ArrayList<Integer>(indexes.subList(originIndexes.size(), indexes.size()));
-		}else{
-			return new ArrayList<Integer>();
-		}
+	public ArrayList<Integer> getWildcardIndexes(){
+		return wildCardIndexes;
 	}
 	
-	public ArrayList<GAEdge> getEdges(){
-		return holonEdges;
+	public ArrayList<GAEdge> getAdditionalEdges(){
+		return additionalEdges;
+	}
+	
+	public ArrayList<GAEdge> getOriginalEdges(){
+		return originEdges;
+	}
+	
+	public ArrayList<GAEdge> getAllEdges(){
+		ArrayList<GAEdge> allEdges = new ArrayList<GAEdge>();
+		allEdges.addAll(additionalEdges);
+		allEdges.addAll(originEdges);
+		return allEdges;
 	}
 	
 	public void addObject(AbstractCpsObject obj){
+		addObjectWithIdx(obj, obj.getId());
+		/*
 		addObjectWithIdx(obj, lastIndex);
 		lastIndex++;
+		*/
 	}
 	
 	public void addObjectWithIdx(AbstractCpsObject obj, int index){
@@ -148,8 +176,11 @@ public class HolegIndividual extends GAIndividual {
 	}
 	
 	public void removeObject(int index){
-		indexToObjectMap.remove(index);
-		indexes.remove((Object)index);
+		AbstractCpsObject toRemove = indexToObjectMap.get(index);
+		HolonWildCard fill = new HolonWildCard("WildCard");
+		fill.setId(toRemove.getId());
+		fill.setPosition(toRemove.getPosition());
+		indexToObjectMap.put(index, fill);
 	}
 	
 	public void addIndex(int index){
@@ -166,7 +197,7 @@ public class HolegIndividual extends GAIndividual {
 	 * posA and posB are the indexes of the Endpoints A and B in the list of Objects
 	 */
 	public void addEdge(int indexA, int indexB){
-		if(!edgeExists(indexA, indexB)){
+		if(!edgeExists(indexA, indexB, getAllEdges())){
 			
 			if(!indexToObjectMap.containsKey(indexA)){
 				CpsNode newObjA = new CpsNode("Node");
@@ -176,17 +207,31 @@ public class HolegIndividual extends GAIndividual {
 				CpsNode newObjB = new CpsNode("Node");
 				addObjectWithIdx(newObjB, indexB);
 			}
-			holonEdges.add(new GAEdge(indexA, indexB, indexToObjectMap.get(indexA), indexToObjectMap.get(indexB)));
+			additionalEdges.add(new GAEdge(indexA, indexB, indexToObjectMap.get(indexA), indexToObjectMap.get(indexB)));
 		
-		}else{
-			addLogEntry("double Edge: " + indexToObjectMap.get(indexA).getId() + " to " 
-					+ indexToObjectMap.get(indexB).getId());
 		}
-
 	}
 	
-	public boolean edgeExists(int indexA, int indexB){
-		for(GAEdge e : holonEdges){
+	public void addOriginalEdge(CpsEdge e){
+		if(indexToObjectMap.containsKey(e.getA().getId()) && indexToObjectMap.containsKey(e.getB().getId())){
+			GAEdge realEdge = new GAEdge(e.getA().getId(), e.getB().getId(),
+					indexToObjectMap.get(e.getA().getId()), indexToObjectMap.get(e.getB().getId()));
+			
+			if(!edgeExists(realEdge.aPos, realEdge.bPos, originEdges)){
+				originEdges.add(realEdge);
+			}
+		}
+	}
+	
+	public void addOriginalEdge(GAEdge e){
+		if(!edgeExists(e.aPos, e.bPos, originEdges)){
+			originEdges.add(new GAEdge(e.aPos, e.bPos, indexToObjectMap.get(e.aPos), 
+					indexToObjectMap.get(e.bPos)));
+		}
+	}
+	
+	public boolean edgeExists(int indexA, int indexB, ArrayList<GAEdge> edges){
+		for(GAEdge e : edges){
 			if((e.aPos == indexA && e.bPos == indexB) || (e.bPos == indexA && e.aPos == indexB)){
 				return true;
 			}
@@ -198,6 +243,10 @@ public class HolegIndividual extends GAIndividual {
 		log += "\n" + entry;
 	}
 	
+	public void resetLog(){
+		log = backupLog;	
+	}
+	
 	public int getAvailableIndex(){
 		for(int i = 0; i <= indexes.size(); i++){
 			if(!indexes.contains(i)){
@@ -206,5 +255,19 @@ public class HolegIndividual extends GAIndividual {
 		}
 		return -1;
 	}
+	
+	
+	public void configurateNetwork(){
+
+		for(GAEdge e : getAllEdges()){
+			e.setA(indexToObjectMap.get(e.aPos));
+			e.setB(indexToObjectMap.get(e.bPos));
+			e.revalidateConnection();
+		}
+	}
+
+	public void setEdgeLength(double doubleValue) {
+		totalEdgeLength = doubleValue;
+	}
 
 }

+ 144 - 107
src/algorithms/geneticAlgorithm/holegGA/Components/HolegMutation.java

@@ -2,6 +2,7 @@ package algorithms.geneticAlgorithm.holegGA.Components;
 
 import java.util.ArrayList;
 import java.util.Collections;
+import java.util.Random;
 
 import classes.AbstractCpsObject;
 import classes.CpsEdge;
@@ -11,16 +12,18 @@ import classes.HolonObject;
 import classes.HolonSwitch;
 import algorithms.geneticAlgorithm.Components.GAMutationStrategy;
 import algorithms.geneticAlgorithm.holegGA.GAEdge;
+import algorithms.geneticAlgorithm.holegGA.ParameterArray;
 
 public class HolegMutation extends GAMutationStrategy<HolegIndividual>{
 	
-	public final int CHANGE_EDGE = 0;
-	public final int ADD_EDGE = 1;
-	public final int REMOVE_EDGE = 2;
-	public final int CHANGE_OBJECT = 3;
-	public final int ADD_OBJECT = 4;
-	public final int REMOVE_OBJECT = 5;
+	public final int ADD_EDGE = 0;
+	public final int REMOVE_EDGE = 1;
+	public final int CHANGE_OBJECT = 0;
+	public final int REMOVE_OBJECT = 1;
 	ArrayList<AbstractCpsObject> objSpace;
+	public boolean editEdges = false;
+	public int maxConnections = 0;
+	public double edgeMutationProb = 0;
 	
 	public HolegMutation(){
 		super();
@@ -32,109 +35,81 @@ public class HolegMutation extends GAMutationStrategy<HolegIndividual>{
 
 	@Override
 	public HolegIndividual mutateIndividual(HolegIndividual mutant) {
-		if(rng.nextDouble() < mutationProb){
-			switch(rng.nextInt(6)){
-			case CHANGE_EDGE : 
-				changeEdge(mutant);
-				break;		
-			case ADD_EDGE : 
+		
+		for(Integer wildIdx : mutant.getWildcardIndexes()){
+			if(rng.nextDouble() < mutationProb){
+				switch(rng.nextInt(2)){
+				case CHANGE_OBJECT :
+					changeObject(mutant, wildIdx);
+					break;
+				case REMOVE_OBJECT :
+					removeObject(mutant, wildIdx);
+					break;
+				}
+			}
+		}
+		
+		ArrayList<GAEdge> mutationEdges = new ArrayList<GAEdge>();
+		
+		int endIdx = 0;
+		boolean isOriginal = false;
+
+		if(editEdges){
+			mutationEdges.addAll(mutant.getOriginalEdges());
+			endIdx = mutationEdges.size(); //originalEdges müssen zuerst mutieren da sie sonst 
+											//verworfen werden falls additional Edge gleiche werte bekommt
+			mutationEdges.addAll(mutant.getAdditionalEdges());
+		}else{
+			mutationEdges.addAll(mutant.getAdditionalEdges());
+		}
+		
+		for(int i = 0; i < mutationEdges.size(); i++){
+			if(rng.nextDouble() < edgeMutationProb){
+				if(i < endIdx){
+					changeSingleEdge(mutant, mutationEdges.get(i), true);
+				}else{
+					changeSingleEdge(mutant, mutationEdges.get(i), false);
+				}
+			}
+		}
+		
+		if(rng.nextDouble() < edgeMutationProb){
+			switch(rng.nextInt(2)){
+			case ADD_EDGE:
 				addEdge(mutant);
 				break;
-			case REMOVE_EDGE : 
+			case REMOVE_EDGE:
 				removeEdge(mutant);
 				break;
-			case CHANGE_OBJECT : 
-				changeObject(mutant);
-				break;
-			case ADD_OBJECT : 
-				addObject(mutant);
-				break;
-			case REMOVE_OBJECT : 
-				removeObject(mutant);
-				break;
 			}
+			
 		}
 		return mutant;
 	}
 
-	public void removeObject(HolegIndividual mutant) {
-		if(mutant.getNonOriginIndexes().size() > 0){
-			int removeIdx = rng.nextInt(mutant.getNonOriginIndexes().size());
-			removeIdx = mutant.getNonOriginIndexes().get(removeIdx);
+	public void removeObject(HolegIndividual mutant, int removeIdx) {
 			ArrayList<CpsEdge> connections = new ArrayList<CpsEdge>();
 			connections.addAll(mutant.getObjectWithIndex(removeIdx).getConnections());
 			for(CpsEdge e : connections){
-				/*
-				if(e.getA() != mutant.getObjectWithIndex(mutant.getNonOriginIndexes().get(removeIdx))){
-					e.getA().getConnections().remove(e);
-				}else{
-					e.getB().getConnections().remove(e);
-				}
-				*/
-		
 				e.getA().getConnections().remove(e);
 				e.getB().getConnections().remove(e);
-		
 			}
-			
 			ArrayList<GAEdge> edgesToRemove = new ArrayList<GAEdge>();
-			for(GAEdge  gE : mutant.getEdges()){
+			for(GAEdge  gE : mutant.getAllEdges()){
 				if(gE.aPos == removeIdx || gE.bPos == removeIdx){
 					edgesToRemove.add(gE);
 				}
 			}
-			mutant.getEdges().removeAll(edgesToRemove);
-			
+			mutant.getAllEdges().removeAll(edgesToRemove);
 			mutant.addLogEntry("Object wit ID " + mutant.indexToObjectMap.get(removeIdx).getId() + " removed");
 			mutant.removeObject(removeIdx);
-		}
 	}
 
-	public void addObject(HolegIndividual mutant) {
-		int objSpaceIdx = rng.nextInt(objSpace.size());
-		int addIndex = mutant.getAvailableIndex();
-		
-		
-		AbstractCpsObject newObj = null;
-		AbstractCpsObject object = objSpace.get(objSpaceIdx);
-		if(object instanceof HolonObject){
-			newObj = new HolonObject(object);
-		}else if(object instanceof HolonSwitch){
-			newObj = new HolonSwitch(object);
-		}else if(object instanceof HolonBattery){
-			newObj = new HolonBattery(object);
-		}else if(object == null){
-			newObj = new CpsNode("Node");
-		}
-		
-		if(mutant.getIndexes().size() > 0){
-			int indexB = mutant.getIndexes().get(rng.nextInt(mutant.getIndexes().size()));
-			mutant.addObjectWithIdx(newObj, addIndex);
-			mutant.addEdge(addIndex, indexB);
-			mutant.addLogEntry("Object with ID " + newObj.getId() + " and Edge between "
-					+ mutant.indexToObjectMap.get(indexB).getId() + " and " + newObj.getId() + " added");
-		}else{
-			mutant.addObjectWithIdx(newObj, addIndex);
-			mutant.addLogEntry("Object with ID " + newObj.getId() + " added");
-		}
-	}
-
-	public void changeObject(HolegIndividual mutant) {
-		if(mutant.getNonOriginIndexes().size() > 0){
-			int changeIdx = rng.nextInt(mutant.getNonOriginIndexes().size());
-			changeIdx = mutant.getNonOriginIndexes().get(changeIdx);
-	
+	public void changeObject(HolegIndividual mutant, int changeIdx) {
+		if(objSpace.size() > 0){
 			AbstractCpsObject newObj = null;
 			AbstractCpsObject absObj = objSpace.get(rng.nextInt(objSpace.size()));
-			if(absObj instanceof HolonObject){
-				newObj = new HolonObject(absObj);
-			}else if(absObj instanceof HolonSwitch){
-				newObj = new HolonSwitch(absObj);
-			}else if(absObj instanceof HolonBattery){
-				newObj = new HolonBattery(absObj);
-			}else if(absObj == null){
-				newObj = new CpsNode("Node");
-			}
+			newObj = absObj.makeCopy();
 		
 			AbstractCpsObject oldObject = mutant.getObjectWithIndex(changeIdx);
 			for(CpsEdge e : oldObject.getConnections()){
@@ -146,41 +121,68 @@ public class HolegMutation extends GAMutationStrategy<HolegIndividual>{
 					newObj.addConnection(e);
 				}
 			}
+			newObj.setId(oldObject.getId());
+			newObj.setPosition(oldObject.getPosition());
+		
 			mutant.indexToObjectMap.put(changeIdx, newObj);
-			mutant.addLogEntry("Object changed");
-			//LogEntry notwendig
+			mutant.addLogEntry("Object with Id " + newObj.getId() + " changed");
 		}
 	}
 
 	public void removeEdge(HolegIndividual mutant) {
-		if(mutant.getEdges().size() > 0){
-			int edgeIdx = rng.nextInt(mutant.getEdges().size());
-			CpsEdge toRemove = mutant.getEdges().get(edgeIdx);
+		ArrayList<GAEdge> edgesSpace = new ArrayList<GAEdge>();
+		int spaceEndIdx = 0;
+		if(editEdges){
+			
+			edgesSpace.addAll(mutant.getAdditionalEdges());
+			spaceEndIdx = edgesSpace.size();
+			edgesSpace.addAll(mutant.getOriginalEdges());
+			
+		}else{
+			edgesSpace.addAll(mutant.getAdditionalEdges());
+			spaceEndIdx = edgesSpace.size();
+		}
+		if(edgesSpace.size() > 0){
+			int edgeIdx = rng.nextInt(edgesSpace.size());
+			CpsEdge toRemove = edgesSpace.get(edgeIdx);
 			toRemove.getA().getConnections().remove(toRemove);
 			toRemove.getB().getConnections().remove(toRemove);
-			mutant.getEdges().remove(toRemove);
-			mutant.addLogEntry("Edge between " + toRemove.getA().getId() + " and "
-				+ toRemove.getB().getId() + " removed");
+			if(edgeIdx < spaceEndIdx){
+				mutant.getAdditionalEdges().remove(edgeIdx);
+			}else{
+				mutant.getOriginalEdges().remove(edgeIdx-spaceEndIdx);
+			}
+			mutant.addLogEntry("Edge (" + toRemove.getA().getId() + ","
+				+ toRemove.getB().getId() + ") removed");
 		}
 	}
 
 	public void addEdge(HolegIndividual mutant) {
-		if(mutant.getIndexes().size() > 1){
-			ArrayList<Integer> list = new ArrayList<Integer>();
-			list.addAll(mutant.getIndexes());
-			Collections.shuffle(list);
-			int aPos = list.get(0);
-			int bPos = list.get(1);
-			mutant.addEdge(aPos, bPos);
-			mutant.addLogEntry("Edge between " + mutant.indexToObjectMap.get(aPos).getId() + 
-				" and " + mutant.indexToObjectMap.get(bPos).getId() + " added");
+		if(mutant.getAllEdges().size() < maxConnections){
+			if(mutant.getIndexes().size() > 1){
+				ArrayList<Integer> list = new ArrayList<Integer>();
+				list.addAll(mutant.getIndexes());
+				Collections.shuffle(list);
+				int aPos = list.get(0);
+				int bPos = list.get(1);
+				mutant.addEdge(aPos, bPos);
+				mutant.addLogEntry("Edge (" + mutant.indexToObjectMap.get(aPos).getId() + 
+					"," + mutant.indexToObjectMap.get(bPos).getId() + ") added");
+			}
 		}
 	}
 
-	public void changeEdge(HolegIndividual mutant) {
-		if(mutant.getEdges().size() > 0){
-			int edgeIdx = rng.nextInt(mutant.getEdges().size());
-			CpsEdge toChange = mutant.getEdges().get(edgeIdx);
+	public void changeRandomEdge(HolegIndividual mutant) {
+		ArrayList<GAEdge> edgeSpace;
+		if(editEdges){
+			edgeSpace = mutant.getAllEdges();
+		}else{
+			edgeSpace = mutant.getAdditionalEdges();
+		}
+		
+		if(edgeSpace.size() > 0){
+			int edgeIdx = rng.nextInt(edgeSpace.size());
+			GAEdge toChange = edgeSpace.get(edgeIdx);
 			boolean changeA = rng.nextBoolean();
 			int randomIndex = rng.nextInt(mutant.getIndexes().size());
 			randomIndex = mutant.getIndexes().get(randomIndex);
@@ -188,28 +190,63 @@ public class HolegMutation extends GAMutationStrategy<HolegIndividual>{
 				toChange.getA().getConnections().remove(toChange);
 				if(toChange.getB() != mutant.getObjectWithIndex(randomIndex)){
 					toChange.setA(mutant.getObjectWithIndex(randomIndex));
+					toChange.aPos = randomIndex;
 					mutant.getObjectWithIndex(randomIndex).getConnections().add(toChange);
 				}else{
 					toChange.getB().getConnections().remove(toChange);
-					mutant.getEdges().remove(toChange);
+					mutant.getAdditionalEdges().remove(toChange);
 				}
 			}else{
 				toChange.getB().getConnections().remove(toChange);
 				if(toChange.getA() != mutant.getObjectWithIndex(randomIndex)){
 					toChange.setB(mutant.getObjectWithIndex(randomIndex));
+					toChange.bPos = randomIndex;
 					mutant.getObjectWithIndex(randomIndex).getConnections().add(toChange);
 				}else{
 					toChange.getA().getConnections().remove(toChange);
-					mutant.getEdges().remove(toChange);
+					mutant.getAdditionalEdges().remove(toChange);
 				}
 			}
-			mutant.addLogEntry("Edge Changed");
 		}
 		
 	}
 	
+	public static void changeSingleEdge(HolegIndividual mutant, GAEdge toChange, boolean isOriginal){
+		boolean changeA = rng.nextBoolean();
+		int randomIndex = rng.nextInt(mutant.getIndexes().size());
+		randomIndex = mutant.getIndexes().get(randomIndex);
+		String logString = "Edge (" + toChange.aPos + "," + toChange.bPos + 
+				") changed to ";
+		if(mutant.getObjectWithIndex(randomIndex) != toChange.getA() &&
+				mutant.getObjectWithIndex(randomIndex) != toChange.getB()){
+			if(changeA && !mutant.edgeExists(randomIndex, toChange.bPos, mutant.getAllEdges())){
+				toChange.getA().getConnections().remove(toChange);
+				toChange.setA(mutant.getObjectWithIndex(randomIndex));
+				toChange.aPos = randomIndex;
+				mutant.getObjectWithIndex(randomIndex).getConnections().add(toChange);
+			}else if(!mutant.edgeExists(randomIndex, toChange.aPos, mutant.getAllEdges())){
+				toChange.getB().getConnections().remove(toChange);
+				toChange.setB(mutant.getObjectWithIndex(randomIndex));
+				toChange.bPos = randomIndex;
+				mutant.getObjectWithIndex(randomIndex).getConnections().add(toChange);
+				}
+		}
+		mutant.addLogEntry(logString + "(" + toChange.aPos + "," + toChange.bPos + ")");
+	}
+	
+	public void setParameters(ParameterArray params){
+		this.edgeMutationProb = (double)params.get(params.EDGE_MUTATION_PROB);
+		this.setMutationProbability((double)params.get(params.WILDCARD_MUTATION_PROB));
+		this.maxConnections = (int)params.get(params.MAX_EDGES);
+		this.editEdges = (boolean)params.get(params.EDIT_EDGES);
+	}
+	
 	public void setObjectSpace(ArrayList<AbstractCpsObject> space){
 		objSpace = space;
 	}
+	
+	public void setEdgeMutationProb(double prob){
+		this.edgeMutationProb = prob;
+	}
 
 }

+ 222 - 0
src/algorithms/geneticAlgorithm/holegGA/Evaluator.java

@@ -0,0 +1,222 @@
+package algorithms.geneticAlgorithm.holegGA;
+
+import java.awt.Color;
+import java.awt.Paint;
+import java.util.ArrayList;
+import java.util.Random;
+
+import javax.swing.JFrame;
+import javax.swing.JPanel;
+
+import org.jfree.chart.ChartFactory;
+import org.jfree.chart.ChartPanel;
+import org.jfree.chart.JFreeChart;
+import org.jfree.chart.plot.PlotOrientation;
+import org.jfree.chart.renderer.xy.XYLineAndShapeRenderer;
+import org.jfree.data.xy.XYSeries;
+import org.jfree.data.xy.XYSeriesCollection;
+import org.jfree.ui.ApplicationFrame;
+import org.jfree.ui.RefineryUtilities;
+public class Evaluator {
+	XYLineAndShapeRenderer maxFitnessRenderer;
+	XYLineAndShapeRenderer maxFoundRenderer;
+	XYLineAndShapeRenderer bestIndividualRenderer;
+	XYLineAndShapeRenderer averageIndividualRenderer;
+	XYLineAndShapeRenderer worstIndividualRenderer;
+	JFreeChart bestIndividualChart;
+	JFreeChart fitnessChart;
+	ChartPanel bestIndividualPanel;
+	ChartPanel fitnessPanel;
+	JFreeChart chart;
+	int seriesCount = 0;
+	
+	public Evaluator(String title){
+		maxFitnessRenderer = new XYLineAndShapeRenderer();
+		maxFitnessRenderer.setSeriesPaint(0, Color.BLACK);
+		maxFitnessRenderer.setSeriesShapesVisible(0, false);
+		maxFoundRenderer = new XYLineAndShapeRenderer();
+		maxFoundRenderer.setSeriesPaint(0, Color.ORANGE);
+		maxFoundRenderer.setSeriesShapesVisible(0, false);
+		bestIndividualRenderer = new XYLineAndShapeRenderer();
+		bestIndividualRenderer.setSeriesPaint(0, Color.GREEN);
+		bestIndividualRenderer.setSeriesShapesVisible(0, false);
+		averageIndividualRenderer= new XYLineAndShapeRenderer();
+		averageIndividualRenderer.setSeriesPaint(0, Color.BLUE);
+		averageIndividualRenderer.setSeriesShapesVisible(0, false);
+		worstIndividualRenderer = new XYLineAndShapeRenderer();
+		worstIndividualRenderer.setSeriesPaint(0, Color.RED);
+		worstIndividualRenderer.setSeriesShapesVisible(0, false);
+		
+		bestIndividualChart = ChartFactory.createXYLineChart(
+				title, 
+				"Generation", 
+				"Fitness",
+				null,
+				PlotOrientation.VERTICAL,
+				true,
+				true,
+				false);
+		
+		fitnessChart = ChartFactory.createXYLineChart(
+				title, 
+				"Generation", 
+				"Fitness",
+				null,
+				PlotOrientation.VERTICAL,
+				true,
+				true,
+				false);
+		
+		bestIndividualChart.getXYPlot().setBackgroundPaint(Color.WHITE);
+		bestIndividualChart.getXYPlot().setDomainGridlinesVisible(true);
+		bestIndividualChart.getXYPlot().setRangeGridlinesVisible(true);
+		bestIndividualChart.getXYPlot().setRangeGridlinePaint(Color.GRAY);
+		bestIndividualChart.getXYPlot().setDomainGridlinePaint(Color.GRAY);
+		//bestIndividualChart.getXYPlot().setDataset(0, data);
+		//bestIndividualChart.getXYPlot().setDataset(1, data2);
+		bestIndividualChart.getXYPlot().setRenderer(1,maxFoundRenderer);
+		bestIndividualChart.getXYPlot().setRenderer(0,maxFitnessRenderer);
+		
+		fitnessChart.getXYPlot().setBackgroundPaint(Color.WHITE);
+		fitnessChart.getXYPlot().setDomainGridlinesVisible(true);
+		fitnessChart.getXYPlot().setRangeGridlinesVisible(true);
+		fitnessChart.getXYPlot().setRangeGridlinePaint(Color.GRAY);
+		fitnessChart.getXYPlot().setDomainGridlinePaint(Color.GRAY);
+		
+		fitnessChart.getXYPlot().setRenderer(0,maxFitnessRenderer);
+
+		fitnessChart.getXYPlot().setRenderer(1,bestIndividualRenderer);
+		fitnessChart.getXYPlot().setRenderer(2,averageIndividualRenderer);
+		fitnessChart.getXYPlot().setRenderer(3,worstIndividualRenderer);
+		
+		
+		bestIndividualPanel = new ChartPanel(bestIndividualChart);
+		bestIndividualPanel.setPreferredSize(new java.awt.Dimension(500, 270));
+		
+		fitnessPanel = new ChartPanel(fitnessChart);
+		fitnessPanel.setPreferredSize(new java.awt.Dimension(500, 270));
+	}
+	
+	public void drawFitnessGraph(ArrayList<Double> best, ArrayList<Double> medium,
+			ArrayList<Double> worst){
+		Random rng = new Random();
+		XYSeries highest = new XYSeries("Best Individual");
+		XYSeries average = new XYSeries("Average Individual");
+		XYSeries lowest = new XYSeries("Worst Individual");
+		XYSeries max = new XYSeries("Maximum Fitness");
+		for(int i = 0; i < 100; i++){
+			highest.add(i,best.get(i));
+			average.add(i,medium.get(i));
+			lowest.add(i,worst.get(i));
+			max.add(i, 32);
+		}
+		XYSeriesCollection maxCol = new XYSeriesCollection(max);
+		XYSeriesCollection averageCol = new XYSeriesCollection(average);
+		XYSeriesCollection lowestCol = new XYSeriesCollection(lowest);
+		XYSeriesCollection highestCol = new XYSeriesCollection(highest);
+		fitnessChart.getXYPlot().setDataset(0, maxCol);
+		fitnessChart.getXYPlot().setDataset(1, highestCol);
+		fitnessChart.getXYPlot().setDataset(2, averageCol);
+		fitnessChart.getXYPlot().setDataset(3, lowestCol);
+		
+		JFrame appFrame = new JFrame("demo");
+		appFrame.setContentPane(fitnessPanel);
+		appFrame.pack();
+		RefineryUtilities.centerFrameOnScreen(appFrame);
+		appFrame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
+
+		appFrame.setVisible(true);
+	}
+	
+	public void drawFoundGraph(ArrayList<Double> found){
+		XYLineAndShapeRenderer worstIndividualRenderer;
+		JFreeChart bestIndividualChart;
+		
+		
+		Random rng = new Random();
+		XYSeries highest = new XYSeries("Best Found");
+		XYSeries max = new XYSeries("Maximum Fitness");
+		for(int i = 0; i < 100; i++){
+			highest.add(i, found.get(i));
+			max.add(i, 32);
+		}
+		XYSeriesCollection maxCol = new XYSeriesCollection(max);
+		XYSeriesCollection highestCol = new XYSeriesCollection(highest);
+		//bestIndividualChart.getXYPlot().setDataset(0, maxCol);
+		//bestIndividualChart.getXYPlot().setDataset(1, highestCol);
+		
+		JFrame appFrame = new JFrame("demo");
+		appFrame.setContentPane(bestIndividualPanel);
+		appFrame.pack();
+		RefineryUtilities.centerFrameOnScreen(appFrame);
+		appFrame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
+
+		appFrame.setVisible(true);
+	}
+	
+	public void initRendering(String title){
+		seriesCount = 0;
+		chart = ChartFactory.createXYLineChart(title, 
+				"Generation", 
+				"Fitness", 
+				null, 
+				PlotOrientation.VERTICAL, 
+				false, 
+				false, 
+				false);
+		chart.getXYPlot().setBackgroundPaint(Color.WHITE);
+		chart.getXYPlot().setDomainGridlinesVisible(true);
+		chart.getXYPlot().setRangeGridlinesVisible(true);
+		chart.getXYPlot().setRangeGridlinePaint(Color.GRAY);
+		chart.getXYPlot().setDomainGridlinePaint(Color.GRAY);
+	}
+	
+	public void initPlottedRendering(String title){
+		seriesCount = 0;
+		chart = ChartFactory.createXYLineChart(title, 
+				"Generation", 
+				"Fitness", 
+				null, 
+				PlotOrientation.VERTICAL, 
+				true, 
+				true, 
+				false);
+		chart.getXYPlot().setBackgroundPaint(Color.WHITE);
+		chart.getXYPlot().setDomainGridlinesVisible(true);
+		chart.getXYPlot().setRangeGridlinesVisible(true);
+		chart.getXYPlot().setRangeGridlinePaint(Color.GRAY);
+		chart.getXYPlot().setDomainGridlinePaint(Color.GRAY);
+	}
+	
+	public void addSeries(ArrayList<Double> series, Color color, String name){
+		Random rng = new Random();
+		Color usedColor;
+		if(color == null){
+			usedColor = new Color(rng.nextFloat(), rng.nextFloat(), rng.nextFloat());
+		}else{
+			usedColor = color;
+		}
+		XYLineAndShapeRenderer renderer = new XYLineAndShapeRenderer();
+		renderer.setSeriesPaint(0, usedColor);
+		renderer.setSeriesShapesVisible(0, false);
+		XYSeries values = new XYSeries(name);
+		for(int i = 0; i < series.size(); i++){
+			values.add(i, series.get(i));
+		}
+		XYSeriesCollection col = new XYSeriesCollection(values);
+		chart.getXYPlot().setDataset(seriesCount, col);
+		chart.getXYPlot().setRenderer(seriesCount, renderer);
+		seriesCount++;
+	}
+	
+	public void drawChart(){
+		ChartPanel chartPanel = new ChartPanel(chart);
+		JFrame graph = new JFrame("");
+		graph.setContentPane(chartPanel);
+		graph.pack();
+		RefineryUtilities.centerFrameOnScreen(graph);
+		graph.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
+		graph.setVisible(true);
+	}
+
+}

+ 9 - 0
src/algorithms/geneticAlgorithm/holegGA/GAEdge.java

@@ -13,5 +13,14 @@ public class GAEdge extends CpsEdge {
 		aPos = a;
 		bPos = b;
 	}
+	
+	public void revalidateConnection(){
+		if(!this.getA().getConnections().contains(this)){
+			this.getA().getConnections().add(this);
+		}
+		if(!this.getB().getConnections().contains(this)){
+			this.getB().getConnections().add(this);
+		}
+	}
 
 }

+ 68 - 136
src/algorithms/geneticAlgorithm/holegGA/GenAlgoHandler.java

@@ -2,14 +2,20 @@ package algorithms.geneticAlgorithm.holegGA;
 
 import java.util.ArrayList;
 
+import javax.swing.JTextField;
+
 import classes.AbstractCpsObject;
 import classes.Category;
 import classes.CpsEdge;
+import classes.CpsNode;
+import classes.HolonWildCard;
 import classes.Position;
 import ui.controller.Control;
 import ui.model.Model;
 import algorithms.geneticAlgorithm.Components.GAResultListener;
+import algorithms.geneticAlgorithm.Components.GASelectionStrategy;
 import algorithms.geneticAlgorithm.Components.GeneticAlgo;
+import algorithms.geneticAlgorithm.Components.Selections.TournamentProportionalSelection;
 import algorithms.geneticAlgorithm.Components.Selections.TournamentRankSelection;
 import algorithms.geneticAlgorithm.Components.Selections.TournamentSelectionStrategy;
 import algorithms.geneticAlgorithm.holegGA.Components.HolegCrossover;
@@ -27,111 +33,78 @@ public class GenAlgoHandler {
 	Control controller;
 	Model model;
 	int genCount;
-	public int popSize;
-	public int tournamentSize;
-	public double tournamentProb;
-	boolean onlyNodes;
+
 	GeneticAlgo<HolegIndividual> holegGA;
-	TournamentRankSelection<HolegIndividual> tRS;
+	TournamentSelectionStrategy tRS;
+	//TournamentRankSelection<HolegIndividual> tRS;
+	//TournamentProportionalSelection<HolegIndividual> tRS;
+	HolegFittnessScenario hF;
 	HolegMutation hM;
 	HolegCrossover hC;
 	ArrayList<AbstractCpsObject> objSpace;
+	CpsNode theNode = new CpsNode("Node");
 	
 	public GenAlgoHandler(Control controller, Model model){
 		this.controller = controller;
 		this.model = model;
 		genCount = 1;
-		popSize = 100;
 		objSpace = new ArrayList<AbstractCpsObject>();
 		for(Category cat : model.getCategories()){
 			for(AbstractCpsObject obj : cat.getObjects()){
-				objSpace.add(obj);
+				if(!(obj instanceof HolonWildCard) && obj.useForGA){
+					objSpace.add(obj);
+				}
 			}
 		}
+		
 		ArrayList<AbstractCpsObject> origin = model.getObjectsOnCanvas();
+		ArrayList<CpsEdge> edges = model.getEdgesOnCanvas();
 		factory = new HolegFactory(objSpace, 0, 0);
-		factory.originObjects = origin;
-		onlyNodes = false;
+		factory.originalObjects = origin;
+		factory.originalEdges = edges;
 		
 		hC = new HolegCrossover();
-		//HolegFittnessFkt hF = new HolegFittnessFkt(controller);
-		HolegFittnessScenario hF = new HolegFittnessScenario(controller);
+		hF = new HolegFittnessScenario(controller);
 		hM = new HolegMutation(0.01);
 		hM.setObjectSpace(objSpace);
-		tRS = new TournamentRankSelection<HolegIndividual>();
-		holegGA = new GeneticAlgo<HolegIndividual>(tRS, hC, hM, hF, factory, popSize);
-	}
-	
-	public void createGeneration(int objAmount, int edgeAmount){
-		factory.maxObjects = objAmount;
-		factory.maxConnections = edgeAmount;
-		factory.onlyNodes = onlyNodes;
-		holegGA.popSize = popSize;
-		tRS.tournamentSize = tournamentSize;
+		tRS = new TournamentSelectionStrategy<HolegIndividual>();
+		//tRS = new TournamentRankSelection<HolegIndividual>();
+		//tRS = new TournamentProportionalSelection<HolegIndividual>();
+		holegGA = new GeneticAlgo<HolegIndividual>(tRS, hC, hM, hF, factory, 0);
 		
-		if(genCount == 1){
-			holegGA.generateRandomPopulation();
-			HolegGeneration holegGen = new HolegGeneration(genCount);
-			holegGen.setGeneration(holegGA.getSortedPopulation());
-			addPopulationListeners(holegGen);
-			//addPopulationListeners(genCount, sortPopulation(holegGA.getPopulation()));
-			//addPopulationListeners(genCount, holegGA.getPopulation());
-		}else{
-			holegGA.createNextGeneration();
-			HolegGeneration holegGen = new HolegGeneration(genCount);
-			holegGen.setGeneration(holegGA.getSortedPopulation());
-			addPopulationListeners(holegGen);
-			//addPopulationListeners(genCount, sortPopulation(holegGA.getPopulation()));
-		}
-		genCount++;
 	}
 	
-	public void mutationTest(int objAmount, int edgeAmount){
-		factory.maxObjects = objAmount;
-		factory.maxConnections = edgeAmount;
-		factory.onlyNodes = onlyNodes;
-		HolegIndividual parent = factory.createRandomIndividual();
-		ArrayList<HolegIndividual> jo = new ArrayList<HolegIndividual>();
-		jo.add(parent);
-		jo.add(parent);
-		HolegGeneration joGen = new HolegGeneration(genCount);
-		joGen.setGeneration(jo);
-		addPopulationListeners(joGen);
-		genCount++;
+	public void createGeneration(int genAmount, ParameterArray params){
+		factory.maxConnections = (int)params.get(params.MAX_EDGES);
+		factory.editEdges = (boolean)params.get(params.EDIT_EDGES);
+		holegGA.popSize = (int)params.get(params.POPULATION_SIZE);
+		tRS.tournamentSize = (int)params.get(params.TOURNAMENT_SIZE);
+		tRS.selectProb = (double)params.get(params.TOURNAMENT_PROB);
+		hF.setParameters(params);
+		
 		
-		ArrayList<HolegIndividual> jo2 = new ArrayList<HolegIndividual>();
-		HolegIndividual removeObject = hC.crossOver(jo).get(0);
-		HolegIndividual addObject = hC.crossOver(jo).get(0);
-		HolegIndividual changeObject = hC.crossOver(jo).get(0);
-		HolegIndividual removeEdge = hC.crossOver(jo).get(0);
-		HolegIndividual addEdge = hC.crossOver(jo).get(0);
-		HolegIndividual changeEdge = hC.crossOver(jo).get(0);
-		hM.removeObject(removeObject);
-		hM.addObject(addObject);
-		hM.changeObject(changeObject);
-		hM.removeEdge(removeEdge);
-		hM.addEdge(addEdge);
-		hM.changeEdge(changeEdge);
-		jo2.add(removeObject);
-		jo2.add(addObject);
-		jo2.add(changeObject);
-		jo2.add(removeEdge);
-		jo2.add(addEdge);
-		jo2.add(changeEdge);
-		HolegGeneration jo2Gen = new HolegGeneration(genCount);
-		jo2Gen.setGeneration(jo2);
-		addPopulationListeners(jo2Gen);
+		if((boolean)params.get(params.NODES_IN_WILDCARDS)){
+			if(!objSpace.contains(theNode)){
+				objSpace.add(theNode);
+			}else{
+				objSpace.remove(theNode);
+			}
+		}
+		hM.setParameters(params);
+		for(int i = 0; i < genAmount; i++){
+			hF.initialize();
+			if(genCount == 1){
+				holegGA.generateRandomPopulation();
+				HolegGeneration holegGen = new HolegGeneration(genCount);
+				holegGen.setGeneration(holegGA.getSortedPopulation());
+				addGenToPopulationListeners(holegGen);
+			}else{
+				holegGA.createNextGeneration();
+				HolegGeneration holegGen = new HolegGeneration(genCount);
+				holegGen.setGeneration(holegGA.getSortedPopulation());
+				addGenToPopulationListeners(holegGen);
+			}
 		genCount++;
-	}
-	
-	public void drawIndividual(HolegIndividual hI){
-		if(hI.drawn){
-			//draws Individual with the positions in the objects
-			drawIndividualWithPos(hI);
-		}else{
-			//draws Individual as a default grid
-			drawIndividualWithoutPos(hI);
-			hI.drawn = true;
 		}
 	}
 	
@@ -139,75 +112,22 @@ public class GenAlgoHandler {
 		model.setObjectsOnCanvas(new ArrayList<AbstractCpsObject>());
 		model.setEdgesOnCanvas(new ArrayList<CpsEdge>());
 		
+		hI.configurateNetwork();
 		for(int i = 0; i < hI.getIndexes().size(); i++){
 			controller.addObjectCanvas(hI.getObjectAt(i));
 		}
 		
-		for(CpsEdge e : hI.getEdges()){
+		for(GAEdge e : hI.getAllEdges()){
 			controller.addEdgeOnCanvas(e);
 		}
-	}
-	
-	public void drawIndividualWithoutPos(HolegIndividual hI){
-		model.setObjectsOnCanvas(new ArrayList<AbstractCpsObject>());
-		model.setEdgesOnCanvas(new ArrayList<CpsEdge>());
 		
-		int originBound = (int) Math.ceil(Math.sqrt(hI.originIndexes.size()));
-		int row = -1;
-		
-		int x = 50;
-		int y = 50;
-		int dist = 100;
-		boolean isX = true;
-		
-		int allBound = (int) Math.ceil(Math.sqrt(hI.indexes.size()));
-		
-		ArrayList<ArrayList<Integer>> objectField = new ArrayList<ArrayList<Integer>>();
-		for(int i = 0; i < hI.originIndexes.size(); i++){
-			if(i % originBound == 0){
-				row++;
-				objectField.add(new ArrayList<Integer>());
-			}
-			objectField.get(row).add(hI.originIndexes.get(i));
-		}
-		
-		row = 0;
-		for(int j = hI.originIndexes.size(); j < hI.indexes.size(); j++){
-			boolean inserted = false;
-			while(!inserted){
-				if(objectField.size() <= row){
-					objectField.add(new ArrayList<Integer>());
-					objectField.get(row).add(hI.indexes.get(j));
-					inserted = true;
-				}else{
-					if(objectField.get(row).size() < allBound){
-						objectField.get(row).add(hI.indexes.get(j));
-						inserted = true;
-					}else{
-						row++;
-					}
-				}
-			}
-		}
-		
-		for(int k = 0; k < objectField.size(); k++){
-			for(int l = 0; l < objectField.get(k).size(); l++){
-				AbstractCpsObject toDraw = hI.getObjectWithIndex(objectField.get(k).get(l));
-				toDraw.setPosition(new Position(x + (l*dist), y +(k*dist)));
-				controller.addObjectCanvas(toDraw);
-			}
-		}
-		
-		for(CpsEdge e : hI.getEdges()){
-			controller.addEdgeOnCanvas(e);
-		}
 	}
 	
 	public void addListener(GAResultListener<HolegIndividual> listener){
 		listeners.add(listener);
 	}
 	
-	public void addPopulationListeners(HolegGeneration holegGen){
+	public void addGenToPopulationListeners(HolegGeneration holegGen){
 		for(GAResultListener<HolegIndividual> listener : listeners){
 			listener.populationCreated(holegGen);
 		}
@@ -229,6 +149,18 @@ public class GenAlgoHandler {
 		return sortedList;
 	}
 	
+	public void setOriginalNetwork(){
+		HolegIndividual originIndividual = new HolegIndividual(model.getObjectsOnCanvas(),
+					model.getEdgesOnCanvas());
+
+		HolegGeneration originalGen = new HolegGeneration(HolegGeneration.ORIGINAL_GEN);
+		hF.calculateFittness(originIndividual);
+		ArrayList<HolegIndividual> population = new ArrayList<HolegIndividual>();
+		population.add(originIndividual);
+		originalGen.setGeneration(population);
+		addGenToPopulationListeners(originalGen);
+	}
+	
 	
 
 }

+ 174 - 1
src/algorithms/geneticAlgorithm/holegGA/GenAlgoInit.java

@@ -1,7 +1,9 @@
 package algorithms.geneticAlgorithm.holegGA;
 
+import java.awt.Color;
 import java.util.ArrayList;
 
+import algorithms.geneticAlgorithm.holegGA.Components.HolegGeneration;
 import classes.AbstractCpsObject;
 import classes.Category;
 import classes.CpsEdge;
@@ -13,7 +15,7 @@ import ui.controller.Control;
 import ui.model.Model;
 
 public class GenAlgoInit {
-	
+	ParameterArray params = new ParameterArray();
 	Control controller;
 	Model model;
 	GenAlgoWindow window;
@@ -27,6 +29,177 @@ public class GenAlgoInit {
 		
 		window = new GenAlgoWindow(controller, model);
 		window.frame.setVisible(true);
+		
+	}
+	
+	public void evaluate(){
+		Thread t = new Thread(){
+			ArrayList<ArrayList<HolegGeneration>> runHistory = new ArrayList<ArrayList<HolegGeneration>>();
+			ArrayList<Double> avgFitness = new ArrayList<Double>();
+			ArrayList<Double> bestFitness = new ArrayList<Double>();
+			ArrayList<Double> maxFitness =  new ArrayList<Double>();
+			ArrayList<Double> maxFound = new ArrayList<Double>();
+			int runs = 30;
+			Double maxValue = 100.0;
+			public void run(){
+				Evaluator plotAvg = new Evaluator("average from all parameters");
+				Evaluator plotBest = new Evaluator("best from all parameters");
+				plotAvg.initPlottedRendering("Average of all parameters");
+				plotBest.initPlottedRendering("Best of all parameters");
+				
+				for(int b = 1; b <= 3; b++){
+					avgFitness = new ArrayList<Double>();
+					bestFitness = new ArrayList<Double>();
+					maxFitness = new ArrayList<Double>();
+					maxFound = new ArrayList<Double>();
+					ParameterArray params = getParameter(b);
+					for(int j = 0; j < 100; j++){
+						avgFitness.add((double) 0);
+						bestFitness.add(0.0);
+						maxFitness.add(maxValue);
+						maxFound.add(0.0);
+					}
+					Evaluator evalAvg = new Evaluator("average " + b);
+					Evaluator evalBest = new Evaluator("best set " + b);
+					Evaluator evalAvgAvg = new Evaluator("avgavg " + b);
+					Evaluator evalAvgBest = new Evaluator("avgBest " + b);
+					evalAvg.initRendering("Average of each run for set " + b);
+					evalBest.initRendering("Best of each run for set " + b);
+					evalAvgAvg.initRendering("Average of all runs for set " + b);
+					evalAvgBest.initRendering("Best of all runs for set " + b);
+					for(int i = 0; i  < runs; i++){
+						GenAlgoWindow tmp = new GenAlgoWindow(controller,model);
+						ArrayList<HolegGeneration> oneRun = tmp.evaluationRun(params);
+						ArrayList<Double> bestOneRun = new ArrayList<Double>();
+						ArrayList<Double> averageOneRun = new ArrayList<Double>();
+						ArrayList<Double> bestFoundOneRun = new ArrayList<Double>();
+						for(int k = 0; k < oneRun.size(); k++){
+							avgFitness.set(k, avgFitness.get(k)+oneRun.get(k).getAvgFittness());
+							bestFitness.set(k, bestFitness.get(k)+oneRun.get(k).getMaxFittness());
+							averageOneRun.add(oneRun.get(k).getAvgFittness());
+							bestOneRun.add(oneRun.get(k).getMaxFittness());
+							if(k != 0){
+								if(oneRun.get(k).getMaxFittness() > bestFoundOneRun.get(k-1)){
+									bestFoundOneRun.add(oneRun.get(k).getMaxFittness());
+								}else{
+									bestFoundOneRun.add(bestFoundOneRun.get(k-1));
+								}
+							}else{
+								bestFoundOneRun.add(oneRun.get(k).getMaxFittness());
+							}
+							maxFound.set(k, maxFound.get(k)+bestFoundOneRun.get(k));
+						}
+						evalAvg.addSeries(averageOneRun, null, "");
+						evalBest.addSeries(bestFoundOneRun, null, "");
+						System.out.println("At run " + i);
+					}
+					for(int z = 0; z < 100; z++){
+						avgFitness.set(z, avgFitness.get(z)/runs);
+						bestFitness.set(z, bestFitness.get(z)/runs);
+						maxFound.set(z, maxFound.get(z)/runs);
+					}
+					evalAvgAvg.addSeries(avgFitness, Color.GRAY, "");
+					evalAvgBest.addSeries(maxFound, Color.BLUE, "");
+					plotAvg.addSeries(avgFitness, getColor(b), "Parameter Set "+ b);
+					plotBest.addSeries(maxFound, getColor(b), "Parameter Set " + b);
+					evalAvg.addSeries(maxFitness, Color.BLACK, "Maximum Fitness");
+					evalAvg.drawChart();
+					evalBest.addSeries(maxFitness, Color.BLACK, "Maximum Fitness");
+					evalBest.drawChart();
+					evalAvgAvg.addSeries(maxFitness, Color.BLACK, "Maximum Fitness");
+					evalAvgAvg.drawChart();
+					evalAvgBest.addSeries(maxFitness, Color.BLACK, "Maximum Fitness");
+					evalAvgBest.drawChart();
+				}
+				plotAvg.addSeries(maxFitness, Color.BLACK, "Maximum Fitness");
+				plotAvg.drawChart();
+				plotBest.addSeries(maxFitness, Color.BLACK, "Maximum Fitness");
+				plotBest.drawChart();
+			}
+		};
+		t.start();
+	}
+	
+	public Color getColor(int i){
+		if(i == 1){
+			return Color.BLUE;
+		}
+		if(i == 2){
+			return Color.GREEN;
+		}else{
+			return Color.RED;
+		}
+	}
+	
+	public ParameterArray getParameter(int i){
+		if(i == 1){
+			return getParameter1();
+		}
+		if(i == 2){
+			return getParameter2();
+		}else{
+			return getParameter3();
+		}
+	}
+	
+	public ParameterArray getParameter1(){
+		ParameterArray params = new ParameterArray();
+		params = getSameParameters();
+		params.set(params.MAX_EDGES, 39);
+		params.set(params.POPULATION_SIZE, 100);
+		params.set(params.TOURNAMENT_SIZE, 50);
+		params.set(params.TOURNAMENT_PROB, 0.15);
+		params.set(params.EDGE_MUTATION_PROB, 0.01);
+		params.set(params.WILDCARD_MUTATION_PROB, 0.01);
+		return params;
+	}
+	
+	public ParameterArray getParameter2(){
+		ParameterArray params = new ParameterArray();
+		params = getSameParameters();
+		params.set(params.MAX_EDGES, 39);
+		params.set(params.POPULATION_SIZE, 100);
+		params.set(params.TOURNAMENT_SIZE, 50);
+		params.set(params.TOURNAMENT_PROB, 0.01);
+		params.set(params.EDGE_MUTATION_PROB, 0.01);
+		params.set(params.WILDCARD_MUTATION_PROB, 0.01);
+
+		return params;
+	}
+	
+	public ParameterArray getParameter3(){
+		ParameterArray params = new ParameterArray();
+		params = getSameParameters();
+		params.set(params.MAX_EDGES, 39);
+		params.set(params.POPULATION_SIZE, 100);
+		params.set(params.TOURNAMENT_SIZE, 1);
+		params.set(params.TOURNAMENT_PROB, 1.0);
+		params.set(params.EDGE_MUTATION_PROB, 0.01);
+		params.set(params.WILDCARD_MUTATION_PROB, 0.01);
+
+		return params;
+	}
+	
+	public ParameterArray getSameParameters(){
+		ParameterArray params = new ParameterArray();
+		params.set(params.MAX_EDGES, 50);
+		params.set(params.EDIT_EDGES, true);
+		params.set(params.POPULATION_SIZE, 100);
+		params.set(params.TOURNAMENT_SIZE, 30);
+		params.set(params.EDGE_BREAK_AMOUNT, 4);
+		params.set(params.SIM_ITERATIONS, 1);
+		params.set(params.EDGE_MUTATION_PROB, 0.0);
+		params.set(params.SUPPLIED_POINTS, 10.0);
+		params.set(params.OVERSUPPLIED_POINTS, 10.0);
+		params.set(params.UNDERSUPPLIED_POINTS, -10.0);
+		params.set(params.LENGTH_POINTS, -0.5);
+		params.set(params.WILDCARD_USAGE, -5.0);
+		params.set(params.WILDCARD_MUTATION_PROB, 0.0);
+		params.set(params.PARTIALSUPPLIED_POINTS, 3.0);
+		params.set(params.OVERPRODUCTION, -10.0);	
+		params.set(params.NODES_IN_WILDCARDS, true);
+		return params;
+		
 	}
 	
 }

+ 249 - 77
src/algorithms/geneticAlgorithm/holegGA/GenAlgoWindow.java

@@ -41,7 +41,13 @@ import javax.swing.JLabel;
 import javax.swing.JCheckBox;
 import javax.swing.JTextArea;
 
+import classes.CpsEdge;
+import java.awt.Font;
+import java.awt.Dimension;
+
 public class GenAlgoWindow implements GAResultListener<HolegIndividual> {
+	
+	public static int NUMBER = 10;
 
 	JFrame frame;
 	Control controller;
@@ -51,13 +57,27 @@ public class GenAlgoWindow implements GAResultListener<HolegIndividual> {
 	DefaultMutableTreeNode treeRoot;
 	HashMap<DefaultMutableTreeNode, HolegIndividual> treeIndiHashmap;
 	GenAlgoHandler algoHandler;
-	private JTextField objectAmountField;
+	ArrayList<DefaultMutableTreeNode> generationNodes = new ArrayList<DefaultMutableTreeNode>();
 	private JTextField edgeAmountField;
-	private JCheckBox chckbxOnlyNodes;
+	private JCheckBox chckbxEditEdges;
 	private JTextArea logArea;
 	private JTextField popSizeField;
 	private JTextField tournamentSizeField;
-	private JTextField tournamentProbField;
+	private JTextField edgeBreakCount;
+	private JTextField iterationsField;
+	ParameterArray params = new ParameterArray();
+	private JTextField edgeMutationField;
+	private JTextField suppliedField;
+	private JTextField oversuppliedField;
+	private JTextField undersuppliedField;
+	private JTextField edgeLengthField;
+	private JTextField wildcardUsageField;
+	private JTextField wildcardMutationField;
+	private JTextField partialSuppliedField;
+	private JTextField overproductionField;
+	private JTextField generationAmountField;
+	private JCheckBox chckbxWildNodes;
+	ArrayList<HolegGeneration> generationHistory = new ArrayList<HolegGeneration>();
 	/**
 	 * Create the application.
 	 */
@@ -66,15 +86,10 @@ public class GenAlgoWindow implements GAResultListener<HolegIndividual> {
 		this.controller = controller;
 		algoHandler = new GenAlgoHandler(controller, model);
 		algoHandler.addListener(this);
+
 		treeIndiHashmap = new HashMap<DefaultMutableTreeNode, HolegIndividual>();
 		initialize();
-		
-		HolegIndividual originIndividual = new HolegIndividual(model.getObjectsOnCanvas());
-		ArrayList<HolegIndividual> originPopulation = new ArrayList<HolegIndividual>();
-		originPopulation.add(originIndividual);
-		HolegGeneration originGen = new HolegGeneration(-1);
-		originGen.setGeneration(originPopulation);
-		populationCreated(originGen);
+		algoHandler.setOriginalNetwork();
 		
 	}
 
@@ -83,7 +98,7 @@ public class GenAlgoWindow implements GAResultListener<HolegIndividual> {
 	 */
 	private void initialize() {
 		frame = new JFrame();
-		frame.setBounds(100, 100, 450, 520);
+		frame.setBounds(100, 100, 444, 700);
 		frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
 		frame.getContentPane().setLayout(new BoxLayout(frame.getContentPane(), BoxLayout.X_AXIS));
 		
@@ -104,99 +119,194 @@ public class GenAlgoWindow implements GAResultListener<HolegIndividual> {
 		genTree.setModel(treeModel);
 		
 		JSplitPane rightSplitPane = new JSplitPane();
-		rightSplitPane.setResizeWeight(0.5);
+		rightSplitPane.setResizeWeight(0.7);
 		rightSplitPane.setOrientation(JSplitPane.VERTICAL_SPLIT);
 		mainSplitPane.setRightComponent(rightSplitPane);
 		
-		JPanel panel = new JPanel();
-		rightSplitPane.setLeftComponent(panel);
+		JPanel parameterPanel = new JPanel();
+		parameterPanel.setPreferredSize(new Dimension(100, 650));
+		JScrollPane parameterScrollView = new JScrollPane();
+		rightSplitPane.setLeftComponent(parameterScrollView);
+		parameterScrollView.setViewportView(parameterPanel);
+
 		
-		JButton btnCreategeneration = new JButton("createGeneration");
-		btnCreategeneration.setBounds(10, 11, 117, 23);
+		JButton btnCreategeneration = new JButton("create N Generations");
+		btnCreategeneration.setBounds(10, 11, 137, 23);
 		btnCreategeneration.addActionListener(new ActionListener() {
 			public void actionPerformed(ActionEvent arg0) {
-				int objAmount = Integer.parseInt(objectAmountField.getText());
-				int edgeAmount = Integer.parseInt(edgeAmountField.getText());
-				algoHandler.onlyNodes = chckbxOnlyNodes.isSelected();
-				algoHandler.popSize = Integer.parseInt(popSizeField.getText());
-				algoHandler.tournamentSize = Integer.parseInt(tournamentSizeField.getText());
-				algoHandler.createGeneration(objAmount, edgeAmount);
+				setParameters();
+				algoHandler.createGeneration(Integer.parseInt(generationAmountField.getText()), params);
 			}
 		});
-		panel.setLayout(null);
-		
-		objectAmountField = new JTextField();
-		objectAmountField.setText("0");
-		objectAmountField.setBounds(111, 45, 86, 20);
-		panel.add(objectAmountField);
-		objectAmountField.setColumns(10);
-		panel.add(btnCreategeneration);
+		parameterPanel.setLayout(null);
+		parameterPanel.add(btnCreategeneration);
 		
 		edgeAmountField = new JTextField();
 		edgeAmountField.setText("0");
-		edgeAmountField.setBounds(111, 76, 86, 20);
-		panel.add(edgeAmountField);
+		edgeAmountField.setBounds(147, 119, 86, 20);
+		parameterPanel.add(edgeAmountField);
 		edgeAmountField.setColumns(10);
 		
-		JLabel lblMaxObjects = new JLabel("Max Objects");
-		lblMaxObjects.setBounds(10, 48, 91, 14);
-		panel.add(lblMaxObjects);
-		
 		JLabel lblMaxEdges = new JLabel("Max Edges");
-		lblMaxEdges.setBounds(10, 79, 91, 14);
-		panel.add(lblMaxEdges);
+		lblMaxEdges.setBounds(10, 122, 91, 14);
+		parameterPanel.add(lblMaxEdges);
 		
-		chckbxOnlyNodes = new JCheckBox("\r\n");
-		chckbxOnlyNodes.setBounds(121, 103, 25, 23);
-		panel.add(chckbxOnlyNodes);
+		chckbxEditEdges = new JCheckBox("\r\n");
+		chckbxEditEdges.setBounds(147, 92, 25, 23);
+		parameterPanel.add(chckbxEditEdges);
 		
-		JLabel lblOnlyNodes = new JLabel("Only Nodes?");
-		lblOnlyNodes.setBounds(10, 107, 91, 14);
-		panel.add(lblOnlyNodes);
+		JLabel lblEditEdges = new JLabel("Edit Edges?");
+		lblEditEdges.setBounds(10, 96, 91, 14);
+		parameterPanel.add(lblEditEdges);
 		
 		popSizeField = new JTextField();
 		popSizeField.setText("100");
-		popSizeField.setBounds(111, 133, 86, 20);
-		panel.add(popSizeField);
+		popSizeField.setBounds(147, 45, 86, 20);
+		parameterPanel.add(popSizeField);
 		popSizeField.setColumns(10);
 		
 		tournamentSizeField = new JTextField();
 		tournamentSizeField.setText("30");
-		tournamentSizeField.setBounds(111, 164, 86, 20);
-		panel.add(tournamentSizeField);
+		tournamentSizeField.setBounds(147, 70, 86, 20);
+		parameterPanel.add(tournamentSizeField);
 		tournamentSizeField.setColumns(10);
 		
-		tournamentProbField = new JTextField();
-		tournamentProbField.setText("0.8");
-		tournamentProbField.setBounds(111, 195, 86, 20);
-		panel.add(tournamentProbField);
-		tournamentProbField.setColumns(10);
-		
 		JLabel lblPopulationSize = new JLabel("Population Size");
-		lblPopulationSize.setBounds(10, 136, 91, 14);
-		panel.add(lblPopulationSize);
+		lblPopulationSize.setBounds(10, 45, 91, 14);
+		parameterPanel.add(lblPopulationSize);
 		
 		JLabel lblTournamentSize = new JLabel("Tournament Size");
-		lblTournamentSize.setBounds(10, 167, 91, 14);
-		panel.add(lblTournamentSize);
+		lblTournamentSize.setBounds(10, 73, 91, 14);
+		parameterPanel.add(lblTournamentSize);
 		
-		JLabel lblTournamentProb = new JLabel("Tournament Prob");
-		lblTournamentProb.setBounds(10, 198, 91, 14);
-		panel.add(lblTournamentProb);
+		edgeBreakCount = new JTextField();
+		edgeBreakCount.setText("0");
+		edgeBreakCount.setBounds(147, 144, 86, 20);
+		parameterPanel.add(edgeBreakCount);
+		edgeBreakCount.setColumns(10);
 		
-		JButton btnMutation = new JButton("mutation");
-		btnMutation.addActionListener(new ActionListener() {
-			public void actionPerformed(ActionEvent arg0) {
-				int objAmount = Integer.parseInt(objectAmountField.getText());
-				int edgeAmount = Integer.parseInt(edgeAmountField.getText());
-				algoHandler.onlyNodes = chckbxOnlyNodes.isSelected();
-				algoHandler.popSize = Integer.parseInt(popSizeField.getText());
-				algoHandler.tournamentSize = Integer.parseInt(tournamentSizeField.getText());
-				algoHandler.mutationTest(objAmount, edgeAmount);
-			}
-		});
-		btnMutation.setBounds(137, 11, 89, 23);
-		panel.add(btnMutation);
+		JLabel lblEdgeBreakProb = new JLabel("Edge Break Amount");
+		lblEdgeBreakProb.setBounds(10, 147, 117, 14);
+		parameterPanel.add(lblEdgeBreakProb);
+		
+		iterationsField = new JTextField();
+		iterationsField.setText("1");
+		iterationsField.setBounds(147, 169, 86, 20);
+		parameterPanel.add(iterationsField);
+		iterationsField.setColumns(10);
+		
+		JLabel lblSimIteration = new JLabel("Sim Iterations");
+		lblSimIteration.setBounds(10, 172, 91, 14);
+		parameterPanel.add(lblSimIteration);
+		
+		edgeMutationField = new JTextField();
+		edgeMutationField.setText("0.01");
+		edgeMutationField.setBounds(147, 194, 86, 20);
+		parameterPanel.add(edgeMutationField);
+		edgeMutationField.setColumns(10);
+		
+		JLabel lblMutationProb = new JLabel("Edge Mutation Prob");
+		lblMutationProb.setBounds(10, 197, 117, 14);
+		parameterPanel.add(lblMutationProb);
+		
+		suppliedField = new JTextField();
+		suppliedField.setText("+10.0");
+		suppliedField.setBounds(147, 297, 86, 20);
+		parameterPanel.add(suppliedField);
+		suppliedField.setColumns(10);
+		
+		JLabel lblFittnesspointsPerAttribute = new JLabel("Fittnesspoints per Attribute:");
+		lblFittnesspointsPerAttribute.setFont(new Font("Tahoma", Font.PLAIN, 12));
+		lblFittnesspointsPerAttribute.setBounds(59, 275, 157, 14);
+		parameterPanel.add(lblFittnesspointsPerAttribute);
+		
+		JLabel lblSuppliedEntity = new JLabel("each supplied Entity");
+		lblSuppliedEntity.setBounds(10, 300, 117, 14);
+		parameterPanel.add(lblSuppliedEntity);
+		
+		oversuppliedField = new JTextField();
+		oversuppliedField.setText("+10.0");
+		oversuppliedField.setBounds(147, 322, 86, 20);
+		parameterPanel.add(oversuppliedField);
+		oversuppliedField.setColumns(10);
+		
+		JLabel lblOversuppliedEntity = new JLabel("each oversupplied Entity");
+		lblOversuppliedEntity.setBounds(10, 325, 127, 14);
+		parameterPanel.add(lblOversuppliedEntity);
+		
+		undersuppliedField = new JTextField();
+		undersuppliedField.setText("-10.0");
+		undersuppliedField.setBounds(147, 347, 86, 20);
+		parameterPanel.add(undersuppliedField);
+		undersuppliedField.setColumns(10);
+		
+		JLabel lblEachUndersuppliedEntity = new JLabel("each undersupplied Entity");
+		lblEachUndersuppliedEntity.setBounds(10, 350, 127, 14);
+		parameterPanel.add(lblEachUndersuppliedEntity);
+		
+		edgeLengthField = new JTextField();
+		edgeLengthField.setText("-1.0");
+		edgeLengthField.setBounds(147, 397, 86, 20);
+		parameterPanel.add(edgeLengthField);
+		edgeLengthField.setColumns(10);
+		
+		JLabel lblForEdge = new JLabel("for 100 edge length");
+		lblForEdge.setBounds(10, 400, 127, 14);
+		parameterPanel.add(lblForEdge);
+		
+		wildcardUsageField = new JTextField();
+		wildcardUsageField.setText("-7.0");
+		wildcardUsageField.setBounds(147, 422, 86, 20);
+		parameterPanel.add(wildcardUsageField);
+		wildcardUsageField.setColumns(10);
+		
+		JLabel lblWildcardUsage = new JLabel("each Wildcard usage");
+		lblWildcardUsage.setBounds(10, 425, 127, 14);
+		parameterPanel.add(lblWildcardUsage);
+		
+		JLabel lblWildcardMutation = new JLabel("Wildcard Mutation Prob");
+		lblWildcardMutation.setBounds(10, 222, 117, 14);
+		parameterPanel.add(lblWildcardMutation);
+		
+		wildcardMutationField = new JTextField();
+		wildcardMutationField.setText("0.01");
+		wildcardMutationField.setBounds(147, 219, 86, 20);
+		parameterPanel.add(wildcardMutationField);
+		wildcardMutationField.setColumns(10);
+		
+		JLabel lblEachPartiallySupplied = new JLabel("each partialsupplied Entity");
+		lblEachPartiallySupplied.setBounds(10, 375, 137, 14);
+		parameterPanel.add(lblEachPartiallySupplied);
+		
+		partialSuppliedField = new JTextField();
+		partialSuppliedField.setText("-2.0");
+		partialSuppliedField.setBounds(147, 372, 86, 20);
+		parameterPanel.add(partialSuppliedField);
+		partialSuppliedField.setColumns(10);
+		
+		JLabel lblForOverproduction = new JLabel("for 1000 overproduction");
+		lblForOverproduction.setBounds(10, 450, 117, 14);
+		parameterPanel.add(lblForOverproduction);
+		
+		overproductionField = new JTextField();
+		overproductionField.setText("-5.0");
+		overproductionField.setBounds(147, 447, 86, 20);
+		parameterPanel.add(overproductionField);
+		overproductionField.setColumns(10);
+		
+		generationAmountField = new JTextField();
+		generationAmountField.setText("1");
+		generationAmountField.setBounds(147, 12, 86, 20);
+		parameterPanel.add(generationAmountField);
+		generationAmountField.setColumns(10);
+		
+		JLabel lblNodesInWildcards = new JLabel("Nodes in Wildcards?");
+		lblNodesInWildcards.setBounds(10, 247, 117, 14);
+		parameterPanel.add(lblNodesInWildcards);
+		
+		chckbxWildNodes = new JCheckBox("");
+		chckbxWildNodes.setBounds(147, 245, 97, 20);
+		parameterPanel.add(chckbxWildNodes);
 		
 		logArea = new JTextArea();
 		rightSplitPane.setRightComponent(logArea);
@@ -230,7 +340,7 @@ public class GenAlgoWindow implements GAResultListener<HolegIndividual> {
 		DefaultMutableTreeNode node = (DefaultMutableTreeNode)selPath.getLastPathComponent();
 		
 		if(treeIndiHashmap.get(node) != null){
-			algoHandler.drawIndividual(treeIndiHashmap.get(node));
+			algoHandler.drawIndividualWithPos(treeIndiHashmap.get(node));
 			logArea.setText(treeIndiHashmap.get(node).log);
 		}
 	}
@@ -239,7 +349,7 @@ public class GenAlgoWindow implements GAResultListener<HolegIndividual> {
 	@Override
 	public void populationCreated(HolegGeneration holegGen) {
 		DefaultMutableTreeNode genNode = new DefaultMutableTreeNode(holegGen);
-		
+		generationHistory.add(holegGen);
 		ArrayList<HolegIndividual> population = holegGen.getGeneration();
 		for(int i = 0; i < population.size(); i++){
 			DefaultMutableTreeNode child = new DefaultMutableTreeNode("Individual " + i);
@@ -247,8 +357,70 @@ public class GenAlgoWindow implements GAResultListener<HolegIndividual> {
 			treeIndiHashmap.put(child, population.get(i));
 			genNode.add(child);
 		}
+		generationNodes.add(genNode);
 		treeRoot.insert(genNode, 0);
-		treeModel.reload();
+		treeModel.reload();	
+		if(holegGen.getGenCount() == HolegGeneration.ORIGINAL_GEN){
+			//edgeAmountField.setText(Integer.toString(holegGen.getGeneration().get(0).getAllEdges().size()));
+			int nodeAmount = holegGen.getGeneration().get(0).getIndexes().size();
+			int maxEdges = (nodeAmount*(nodeAmount-1))/2;
+			edgeAmountField.setText(Integer.toString(maxEdges));
+
+			params.set(params.ORIGINAL_NETWORK, holegGen.getGeneration().get(0));
+		}
+	}
+	
+	
+	
+	/**
+	 * sets All Parameters from the Textfields into the ParameterArray;
+	 */
+	public void setParameters(){
+		params.set(params.MAX_EDGES, Integer.parseInt(edgeAmountField.getText()));
+		params.set(params.EDIT_EDGES, chckbxEditEdges.isSelected());
+		params.set(params.POPULATION_SIZE, Integer.parseInt(popSizeField.getText()));
+		params.set(params.TOURNAMENT_SIZE, Integer.parseInt(tournamentSizeField.getText()));
+		params.set(params.EDGE_BREAK_AMOUNT, Integer.parseInt(edgeBreakCount.getText()));
+		params.set(params.SIM_ITERATIONS, Integer.parseInt(iterationsField.getText()));
+		params.set(params.EDGE_MUTATION_PROB, Double.parseDouble(edgeMutationField.getText()));
+		params.set(params.SUPPLIED_POINTS, Double.parseDouble(suppliedField.getText()));
+		params.set(params.OVERSUPPLIED_POINTS, Double.parseDouble(oversuppliedField.getText()));
+		params.set(params.UNDERSUPPLIED_POINTS, Double.parseDouble(undersuppliedField.getText()));
+		params.set(params.LENGTH_POINTS, Double.parseDouble(edgeLengthField.getText()));
+		params.set(params.WILDCARD_USAGE, Double.parseDouble(wildcardUsageField.getText()));
+		params.set(params.WILDCARD_MUTATION_PROB, Double.parseDouble(wildcardMutationField.getText()));
+		params.set(params.PARTIALSUPPLIED_POINTS, Double.parseDouble(partialSuppliedField.getText()));
+		params.set(params.OVERPRODUCTION, Double.parseDouble(overproductionField.getText()));	
+		params.set(params.NODES_IN_WILDCARDS, chckbxWildNodes.isSelected());
+		params.set(params.TOURNAMENT_PROB, 0.15);
+	}
+	
+	public ArrayList<HolegGeneration> evaluationRun(ParameterArray params){
+		generationHistory = new ArrayList<HolegGeneration>();
+		params.set(params.ORIGINAL_NETWORK, this.params.get(params.ORIGINAL_NETWORK));
+		algoHandler.createGeneration(100, params);
+		return generationHistory;
 		
 	}
+	
+	public void setEvalParameters(ParameterArray params){
+		this.params = params;
+		/*params.set(params.MAX_EDGES, 50);
+		params.set(params.EDIT_EDGES, true);
+		params.set(params.POPULATION_SIZE, 100);
+		params.set(params.TOURNAMENT_SIZE, 30);
+		params.set(params.EDGE_BREAK_AMOUNT, 4);
+		params.set(params.SIM_ITERATIONS, 1);
+		params.set(params.EDGE_MUTATION_PROB, 0.01);
+		params.set(params.SUPPLIED_POINTS, 10.0);
+		params.set(params.OVERSUPPLIED_POINTS, 10.0);
+		params.set(params.UNDERSUPPLIED_POINTS, -10.0);
+		params.set(params.LENGTH_POINTS, -1.0);
+		params.set(params.WILDCARD_USAGE, -5.0);
+		params.set(params.WILDCARD_MUTATION_PROB, 0.05);
+		params.set(params.PARTIALSUPPLIED_POINTS, 3.0);
+		params.set(params.OVERPRODUCTION, -5.0);	
+		params.set(params.NODES_IN_WILDCARDS, true);
+		*/
+	}
 }

+ 43 - 0
src/algorithms/geneticAlgorithm/holegGA/ParameterArray.java

@@ -0,0 +1,43 @@
+package algorithms.geneticAlgorithm.holegGA;
+
+import java.util.ArrayList;
+
+public class ParameterArray {
+	
+	public static int POPULATION_SIZE = 0;
+	public static int TOURNAMENT_SIZE = 1;
+	public static int EDIT_EDGES = 2;
+	public static int MAX_EDGES = 3;
+	public static int EDGE_BREAK_AMOUNT = 4;
+	public static int SIM_ITERATIONS = 5;
+	public static int EDGE_MUTATION_PROB = 6;
+	public static int SUPPLIED_POINTS = 7;
+	public static int UNDERSUPPLIED_POINTS = 8;
+	public static int OVERSUPPLIED_POINTS = 9;
+	public static int LENGTH_POINTS = 10;
+	public static int WILDCARD_MUTATION_PROB = 11;
+	public static int PARTIALSUPPLIED_POINTS = 12;
+	public static int WILDCARD_USAGE = 13;
+	public static int OVERPRODUCTION = 14;
+	public static int NODES_IN_WILDCARDS = 15;
+	public static int OBJECT_SPACE = 16;
+	public static int ORIGINAL_NETWORK = 17;
+	public static int TOURNAMENT_PROB = 18;
+	
+	public ArrayList<Object> list = new ArrayList<Object>();
+	
+	public ParameterArray(){
+		for(int i = 0; i < 19; i++){
+			list.add(new Object());
+		}
+	}
+	
+	public Object get(int index){
+		return list.get(index);
+	}
+	
+	public <T extends Object> void set(int index, T object){
+		list.set(index, object);
+	}
+
+}

+ 8 - 8
src/classes/AbstractCpsObject.java

@@ -44,6 +44,8 @@ public abstract class AbstractCpsObject {
 	ArrayList<Integer> tags;
 	/* a Tag that can be used */
 	ArrayList<Integer> pseudoTags;
+	/* indicates wheter this object is used for the genetic Algorithm */
+	public boolean useForGA = false;
 
 	/**
 	 * Constructor for a CpsObejct with an unique ID.
@@ -75,6 +77,8 @@ public abstract class AbstractCpsObject {
 		setPosition(new Position());
 		setId(IdCounter.nextId());
 		setImage(obj.getImage());
+		tags = new ArrayList<>();
+		pseudoTags = new ArrayList<>();
 	}
 
 	/**
@@ -172,14 +176,6 @@ public abstract class AbstractCpsObject {
 		this.connections = arrayList;
 	}
 
-	/**
-	 * List of all existing connections.
-	 * 
-	 * @return the connections ArrayList
-	 */
-	public ArrayList<CpsEdge> getConnectedTo() {
-		return connections;
-	}
 
 	/**
 	 * Add a new connection to the selected Object.
@@ -355,6 +351,10 @@ public abstract class AbstractCpsObject {
 		}
 	}
 	
+	/**
+	 * needed for Genetic Algorithm
+	 * @return
+	 */
 	public abstract AbstractCpsObject makeCopy();
 
 }

+ 37 - 0
src/classes/HolonWildCard.java

@@ -0,0 +1,37 @@
+package classes;
+
+import java.util.ArrayList;
+
+public class HolonWildCard extends AbstractCpsObject {
+	
+	AbstractCpsObject holdingObject;
+	
+	public HolonWildCard(String objName){
+		super(objName);
+		this.setConnections(new ArrayList<CpsEdge>());
+		this.setImage("/Images/wildCard.png");
+		this.setSav("CVS");
+		this.setId(IdCounter.nextId());
+		holdingObject = this;
+	}
+
+	public HolonWildCard(AbstractCpsObject obj) {
+		super(obj);
+		holdingObject = this;
+		
+	}
+
+	@Override
+	public AbstractCpsObject makeCopy() {
+		return new HolonWildCard(this);
+	}
+	
+	public void setHoldingObject(AbstractCpsObject object){
+		this.holdingObject = object;
+	}
+	
+	public AbstractCpsObject getHoldingObject(){
+		return holdingObject;
+	}
+
+}

+ 3 - 0
src/classes/SubNet.java

@@ -13,6 +13,9 @@ public class SubNet {
 	private ArrayList<CpsEdge> subNetEdges;
 	private ArrayList<HolonSwitch> subNetSwitches;
 	private ArrayList<HolonBattery> subNetBatteries;
+	
+	//for genetic Algorithm. The spare energy which is used by nobody
+	public float spareProduction = 0;
 	/**
 	 * Constructor for a Subnet.
 	 * 

+ 5 - 5
src/ui/controller/CanvasController.java

@@ -140,7 +140,7 @@ public class CanvasController {
 				}
 			}
 			if (!model.getClipboradObjects().contains(cps)) {
-				cps.getConnectedTo().remove(e);
+				cps.getConnections().remove(e);
 			}
 			model.getEdgesOnCanvas().remove(e);
 		}
@@ -245,20 +245,20 @@ public class CanvasController {
 		// Edges
 		boolean newEdge = true;
 		for (AbstractCpsObject cps : model.getClipboradObjects()) {
-			for (CpsEdge e : cps.getConnectedTo()) {
+			for (CpsEdge e : cps.getConnections()) {
 				// A and B of e in the copied Elements?
 				if (model.getClipboradObjects().indexOf(e.getA()) != -1
 						&& model.getClipboradObjects().indexOf(e.getB()) != -1) {
 					AbstractCpsObject a = tempList.get(model.getClipboradObjects().indexOf(e.getA()));
 					AbstractCpsObject b = tempList.get(model.getClipboradObjects().indexOf(e.getB()));
 					// was this Edge created or not?
-					for (CpsEdge et : tempList.get(model.getClipboradObjects().indexOf(cps)).getConnectedTo()) {
-						for (CpsEdge etA : et.getA().getConnectedTo()) {
+					for (CpsEdge et : tempList.get(model.getClipboradObjects().indexOf(cps)).getConnections()) {
+						for (CpsEdge etA : et.getA().getConnections()) {
 							if (et.getA() == a && et.getB() == b) {
 								newEdge = false;
 							}
 						}
-						for (CpsEdge etB : et.getB().getConnectedTo()) {
+						for (CpsEdge etB : et.getB().getConnections()) {
 							if (et.getA() == a && et.getB() == b) {
 								newEdge = false;
 							}

+ 7 - 0
src/ui/controller/CategoryController.java

@@ -9,6 +9,7 @@ import classes.HolonElement;
 import classes.HolonObject;
 import classes.HolonSwitch;
 import classes.HolonTransformer;
+import classes.HolonWildCard;
 import classes.Pair;
 import interfaces.CategoryListener;
 import ui.model.Model;
@@ -207,6 +208,12 @@ public class CategoryController {
 		holonSwitch.setSav(cat.getName());
 		addObject(cat, holonSwitch);
 	}
+	
+	public void addNewWildCard(Category cat, String objName){
+		HolonWildCard wildCard = new HolonWildCard(objName);
+		wildCard.setSav(cat.getName());
+		addObject(cat, wildCard);
+	}
 	/**
 	 * Add new Holon Battery
 	 * @param cat 

+ 11 - 0
src/ui/controller/Control.java

@@ -242,6 +242,17 @@ public class Control {
         saveCategory();
     }
     
+    /**
+     * Add new Wild Card to a Category
+     * @param cat Category
+     * @param obj Wildcard Name
+     * @throws IOException
+     */
+    public void addWildCard(Category cat, String obj) throws IOException {
+    	categoryController.addNewWildCard(cat, obj);
+    	saveCategory();
+    }
+    
     /**
      * Add new HolonBattery to a Category
      * @param cat

+ 1 - 1
src/ui/controller/NodeController.java

@@ -514,7 +514,7 @@ class NodeController {
 				}
 			}
 			if (!model.getClipboradObjects().contains(cps) && !(cps instanceof CpsUpperNode)) {
-				cps.getConnectedTo().remove(e);
+				cps.getConnections().remove(e);
 			}
 			upperNode.getNodeEdges().remove(e);
 		}

+ 25 - 3
src/ui/controller/SimulationManager.java

@@ -172,6 +172,15 @@ public class SimulationManager {
 						//no break must be calculatet for all break; //because no more energy
 					}
 				}
+				
+				/**
+				 * @author Dominik
+				 * for genetic Algorithm -> the total oversupplied energy after battery and 
+				 * consumption calculation is needed. Its the amount of energy which is 
+				 * evenly distributed amongst the consumers in the next step
+				 */
+				singleSubNet.spareProduction = currentProduction;
+				
 				//Over_Supply all consumer equal
 				long nOConsumer = singleSubNet.getObjects().stream().filter(hl -> (hl.getCurrentEnergyAtTimeStep(x) < 0)).count();			
 				if(nOConsumer != 0)
@@ -188,6 +197,8 @@ public class SimulationManager {
 					}
 					currentProduction = 0;
 				}
+				//for genetic Algorithm -> determine whether there is unused energy in the subnet
+				//e.g a subnet which consists of only power plants can't even oversupply
 			}
 			else
 			{
@@ -299,6 +310,7 @@ public class SimulationManager {
 				}
 				
 			}
+			
 			//Visualize the Color
 			for(HolonObject hO : singleSubNet.getObjects())
 			{
@@ -360,7 +372,7 @@ public class SimulationManager {
 					.stream()
 					.filter(hl -> (hl.getState() != HolonObject.NO_ENERGY
 							&& hl.getState() != HolonObject.PRODUCER && hl
-							.getConnectedTo().stream()
+							.getConnections().stream()
 							.filter(e -> (e.getFlow() > 0)).count() > 0))
 					.count();
 			if (numberOfConsumers != 0)
@@ -371,7 +383,7 @@ public class SimulationManager {
 			if (hl.getState() != HolonObject.NO_ENERGY
 					&& hl.getState() != HolonObject.PRODUCER) {
 				for (int i = 0; i < hl.getConnections().size(); i++) {
-					CpsEdge edge = hl.getConnectedTo().get(i);
+					CpsEdge edge = hl.getConnections().get(i);
 					if (edge.isWorking()
 							&& edge.getFlow() > 0
 							|| edge.getCapacity() == CpsEdge.CAPACITY_INFINITE) {
@@ -986,8 +998,18 @@ public class SimulationManager {
 	 * @return boolean
 	 */
 	private boolean legitState(AbstractCpsObject current) {
-		return !(current instanceof HolonSwitch)
+		//Wildcards act like open switches
+		if(current instanceof HolonSwitch){
+			return ((HolonSwitch) current).getState(timeStep);
+		}else if(current instanceof HolonWildCard){
+			return false;
+		}else{
+			return true;
+		}
+		/*
+		return !(current instanceof HolonSwitch || current instanceof HolonWildCard)
 				|| ((HolonSwitch) current).getState(timeStep);
+				*/
 	}
 
 	// /**

+ 13 - 1
src/ui/view/AlgorithmMenu.java

@@ -30,7 +30,8 @@ public class AlgorithmMenu extends JMenu {
 	private static final long serialVersionUID = 1L;
 
 	GenAlgoWindow genAlgoWindow;
-	JMenuItem geneticAlgoBtn = new JMenuItem("Build Network");
+	JMenuItem geneticAlgoBtn = new JMenuItem("Build Network"); //opens the window for gen algo
+	JMenuItem evaluateAlgoBtn = new JMenuItem("Evaluate Algorithm"); //evaluates the gen algo
 	JMenuItem algoFolderButton = new JMenuItem("Select Algorithm Folder");
 	// root Directory
 	File root = null;
@@ -119,9 +120,20 @@ public class AlgorithmMenu extends JMenu {
 			}
 			
 		});
+		
+		evaluateAlgoBtn.addActionListener(new ActionListener(){
+
+			@Override
+			public void actionPerformed(ActionEvent arg0) {
+				GenAlgoInit algoInit = new GenAlgoInit(controller, model);
+				algoInit.evaluate();
+				
+			}
+		});
 
 		// Add to Panel
 		this.add(geneticAlgoBtn);
+		this.add(evaluateAlgoBtn);
 		this.add(algoFolderButton);
 		this.add(mnSelectAlgorithm);
 		mnSelectAlgorithm.add(noneItem);

+ 29 - 3
src/ui/view/GUI.java

@@ -133,6 +133,7 @@ public class GUI implements CategoryListener {
 	private final JTabbedPane tabbedPaneSplit = new JTabbedPane(JTabbedPane.TOP);
 	private final JPopupMenu popmenuEdit = new JPopupMenu();
 	private final JMenuItem editItem = new JMenuItem("Edit Object");
+	private final JCheckBoxMenuItem useForAlgoItem = new JCheckBoxMenuItem("Use for GA?");
 	private final StatisticPanel statSplitPane;
 	private final JScrollPane statScrollPane;
 	private final JLabel maxGraph = new JLabel("100%");
@@ -209,6 +210,9 @@ public class GUI implements CategoryListener {
 	private final JMenuItem mItemObject = new JMenuItem("Object");
 	private final JMenuItem mItemSwitch = new JMenuItem("Switch");
 	private final JMenuItem mItemBattery = new JMenuItem("Battery");
+	
+	private final JMenuItem mItemWildCard = new JMenuItem("WildCard");
+	
 	private final JButton btnDel = new JButton("Delete");
 	private final JButton btnAddHolEL = new JButton("New Element");
 	private final JButton btnDelHolEL = new JButton("Delete Element");
@@ -891,7 +895,8 @@ public class GUI implements CategoryListener {
 
 					JScrollPane scrollPane = getScrollPaneFromTabbedPane();
 
-					if (scrollPane.getViewport().getComponent(0) instanceof UpperNodeCanvas) {
+					if (scrollPane != null &&
+							scrollPane.getViewport().getComponent(0) instanceof UpperNodeCanvas) {
 						scrollPane.getViewport().getComponent(0).repaint();
 					} else {
 						canvas.repaint();
@@ -1895,6 +1900,9 @@ public class GUI implements CategoryListener {
 								{
 									h = new HolonBattery(tempCps);
 								}
+								if (tempCps instanceof HolonWildCard){
+									h = new HolonWildCard(tempCps);
+								}
 								h.setPosition(x, y);
 
 								/**
@@ -1933,6 +1941,9 @@ public class GUI implements CategoryListener {
 							{
 								h = new HolonBattery(tempCps);
 							}
+							if (tempCps instanceof HolonWildCard){
+								h = new HolonWildCard(tempCps);
+							}
 							h.setPosition(x, y);
 							
 							/**
@@ -1965,6 +1976,7 @@ public class GUI implements CategoryListener {
 		
 
 		popmenuEdit.add(editItem);
+		popmenuEdit.add(useForAlgoItem);
 		editItem.setEnabled(false);
 		editItem.addActionListener(actionEvent -> {
 		});
@@ -1998,13 +2010,18 @@ public class GUI implements CategoryListener {
 							for (AbstractCpsObject cps : cat.getObjects()) {
 								if (actualObjectClicked.compareTo(cps
 										.getObjName()) == 0
-										&& !(cps instanceof HolonSwitch)) {
-									editItem.setEnabled(true);
+										/*&& !(cps instanceof HolonSwitch)*/) {
+									editItem.setEnabled(false);
 									popmenuEdit.show(e.getComponent(),
 											e.getX(), e.getY());
 									catOfObjToBeEdited = selectedNode
 											.getParent().toString();
 									tempCps = cps;
+									useForAlgoItem.setSelected(tempCps.useForGA);
+									if(!(cps instanceof HolonSwitch) && 
+											!(cps instanceof HolonWildCard)){
+										editItem.setEnabled(true);
+									}
 								}
 							}
 						}
@@ -2048,6 +2065,11 @@ public class GUI implements CategoryListener {
 			addObjectPopUP.setController(controller);
 			addObjectPopUP.setVisible(true);
 		});
+		useForAlgoItem.addItemListener((new ItemListener() {
+		      public void itemStateChanged(ItemEvent e) {
+		          tempCps.useForGA = useForAlgoItem.isSelected();
+		        }
+		      }));
 		scrollPane1.setViewportView(tree);
 
 		scrollPane1.setColumnHeaderView(panel);
@@ -2082,6 +2104,10 @@ public class GUI implements CategoryListener {
 		mItemBattery.addActionListener(actionEvent -> {
 			new NewPopUp(controller,Option.Battery, frmCyberPhysical);
 		});
+		btnAddPopUp.add(mItemWildCard);
+		mItemWildCard.addActionListener(actionEvent -> {
+			new NewPopUp(controller,Option.WildCard, frmCyberPhysical);
+		});
 		btnAdd.addActionListener(actionEvent -> btnAddPopUp.show(btnAdd, -1, +20));
 		btnAdd.setToolTipText("Add a new Category or Item to the library.");
 		toolBar.add(btnAdd);

+ 49 - 3
src/ui/view/NewPopUp.java

@@ -23,11 +23,11 @@ import ui.controller.Control;
 
 public class NewPopUp extends JDialog{
 	//DefaultConstructor
-	String[] optionStrings = { "","Category", "Object", "Battery", "Switch"};
+	String[] optionStrings = { "","Category", "Object", "Battery", "Switch", "WildCard"};
 	public static enum Option {
-		None, Category, Object, Battery, Switch;
+		None, Category, Object, Battery, Switch, WildCard;
 		public static Option getEnumAtIndex(int desired){
-			if(desired>=0 && desired<=4)
+			if(desired>=0 && desired<=5)
 				return values()[desired];
 			else 
 				return None;
@@ -105,6 +105,9 @@ public class NewPopUp extends JDialog{
 		case Switch:
 			content = makeSwitchPanel();
 			break;
+		case WildCard:
+			content = makeWildCardPanel();
+			break;
 		default:
 			content = makeNothingPanel();
 			break;
@@ -260,6 +263,40 @@ public class NewPopUp extends JDialog{
 		objectPanel.add(inputNameSwitch);
 		return objectPanel;
 	}	
+	
+	private JPanel makeWildCardPanel()
+	{
+		JPanel objectPanel = new JPanel();
+		JLabel categoryText = new JLabel("In Category:");
+		objectPanel.add(categoryText);
+		selectedCategorySwitch = new JComboBox<String>(actualController.getCategoriesStrings());
+		objectPanel.add(selectedCategorySwitch);
+		
+		
+		JLabel switchName = new JLabel("Name:");
+		String initialText = "The name of the new Wild Card";
+		
+		inputNameSwitch.setText(initialText);
+		inputNameSwitch.setBackground(java.awt.Color.LIGHT_GRAY);
+		inputNameSwitch.addFocusListener(new java.awt.event.FocusAdapter() {
+		    public void focusGained(java.awt.event.FocusEvent evt) {
+		       if (inputNameSwitch.getText().equals(initialText)) {
+		    	   inputNameSwitch.setText("");
+		    	   inputNameSwitch.setBackground(java.awt.Color.WHITE);
+		       }
+		    }
+		    public void focusLost (java.awt.event.FocusEvent evt) {
+			       if (inputNameSwitch.getText().equals("")) {
+			    	   inputNameSwitch.setText(initialText);
+			    	   inputNameSwitch.setBackground(java.awt.Color.LIGHT_GRAY);
+			       }
+			    }
+		});
+		inputNameSwitch.setColumns(20);
+		objectPanel.add(switchName);
+		objectPanel.add(inputNameSwitch);
+		return objectPanel;
+	}
 	private void addSaveButtonLogik() {
 		saveButton.addActionListener(actionEvent -> {
 			if(actualOption == Option.Category)
@@ -280,6 +317,15 @@ public class NewPopUp extends JDialog{
 				}
 				dispose();
 			}
+			else if (actualOption == Option.WildCard)
+			{//TODO
+				try {
+					actualController.addWildCard(actualController.searchCategory(selectedCategorySwitch.getSelectedItem().toString()), inputNameSwitch.getText());
+				} catch (IOException e) {
+					System.err.println("IOException addWildcard");
+				}
+				dispose();
+			}
 		});
 	}
 }

+ 1 - 1
tests/tests/PraktikumHolonsTestCanvasController.java

@@ -140,7 +140,7 @@ public class PraktikumHolonsTestCanvasController {
 			}
 
 			// test how many connections current vertice got
-			assertTrue("Number of Connections does not Match: " + mp.searchByID(i).getConnectedTo().size()+ " != " + (i - 1), mp.searchByID(i).getConnectedTo().size() == i - 1);
+			assertTrue("Number of Connections does not Match: " + mp.searchByID(i).getConnections().size()+ " != " + (i - 1), mp.searchByID(i).getConnections().size() == i - 1);
 			// actually just means if its a
 			// complete graph -> all vertices connected all other vertices
 			n = model.getObjectsOnCanvas().size();