Browse Source

AlgoFramework implemented

Tom 4 years ago
parent
commit
ca57adfc0b

+ 131 - 12
src/api/AlgorithmFramework.java

@@ -10,20 +10,32 @@ import java.io.File;
 import java.io.FileOutputStream;
 import java.io.IOException;
 import java.io.OutputStreamWriter;
+import java.math.RoundingMode;
+import java.text.NumberFormat;
 import java.util.ArrayList;
 import java.util.LinkedList;
 import java.util.List;
+import java.util.Locale;
+import java.util.function.Consumer;
+import java.util.function.DoubleConsumer;
+import java.util.function.IntConsumer;
 import java.util.stream.Collectors;
 
 import javax.swing.BorderFactory;
+import javax.swing.Box;
+import javax.swing.BoxLayout;
 import javax.swing.ImageIcon;
 import javax.swing.JButton;
+import javax.swing.JCheckBox;
 import javax.swing.JFileChooser;
+import javax.swing.JFormattedTextField;
+import javax.swing.JLabel;
 import javax.swing.JOptionPane;
 import javax.swing.JPanel;
 import javax.swing.JProgressBar;
 import javax.swing.JScrollPane;
 import javax.swing.JSplitPane;
+import javax.swing.text.NumberFormatter;
 
 import classes.AbstractCpsObject;
 import classes.CpsUpperNode;
@@ -45,6 +57,7 @@ public abstract class AlgorithmFramework implements AddOn{
 	//Panel
 	private JPanel content = new JPanel();
 	protected Console console = new Console();
+	private JPanel borderPanel = new JPanel();
 	
 	
 	//Settings groupNode
@@ -61,7 +74,6 @@ public abstract class AlgorithmFramework implements AddOn{
 	private long startTime;
 	
 	
-	
 	private RunProgressBar runProgressbar = new RunProgressBar();
 	
 	
@@ -76,6 +88,10 @@ public abstract class AlgorithmFramework implements AddOn{
 	
 	//printing
 	protected RunDataBase db;
+	private RunPrinter printer = new RunPrinter("plott.txt");
+
+
+
 	
 	
 	public AlgorithmFramework(){
@@ -92,7 +108,7 @@ public abstract class AlgorithmFramework implements AddOn{
 	
 	
 	
-	public JPanel createOptionPanel() {
+	private JPanel createOptionPanel() {
 		JPanel optionPanel = new JPanel(new BorderLayout());
 		JScrollPane scrollPane = new JScrollPane(createParameterPanel());
 		scrollPane.setBorder(BorderFactory.createTitledBorder("Parameter"));
@@ -104,22 +120,27 @@ public abstract class AlgorithmFramework implements AddOn{
 	private Component createParameterPanel() {
 		JPanel parameterPanel = new JPanel(null);
 		parameterPanel.setPreferredSize(new Dimension(510,300));
+		borderPanel.setLayout(new BoxLayout(borderPanel, BoxLayout.PAGE_AXIS));
+		addIntParameter("Rounds", rounds, intInput -> rounds = intInput, 1);
+		JScrollPane scrollPane = new JScrollPane(borderPanel);
+		scrollPane.setBounds(10, 0, 450, 292);
+		scrollPane.setBorder(BorderFactory.createEmptyBorder());
+		parameterPanel.add(scrollPane);	
+		
 		
-		JProgressBar progressBar = runProgressbar.getJProgressBar();
-		progressBar.setBounds(350, 155, 185, 20);
-		progressBar.setStringPainted(true);
-		parameterPanel.add(progressBar);
 		
 		JButton selectGroupNodeButton = new JButton("Select GroupNode");
-		selectGroupNodeButton.setBounds(350, 120, 185, 30);
+		selectGroupNodeButton.setBounds(500, 0, 185, 30);
 		selectGroupNodeButton.addActionListener(actionEvent -> selectGroupNode());
 		parameterPanel.add(selectGroupNodeButton);	
-		
-		
+		JProgressBar progressBar = runProgressbar.getJProgressBar();
+		progressBar.setBounds(500, 35, 185, 20);
+		progressBar.setStringPainted(true);
+		parameterPanel.add(progressBar);
 		
 		return parameterPanel;
 	}
-	public JPanel createButtonPanel() {
+	private JPanel createButtonPanel() {
 		JPanel buttonPanel = new JPanel(new FlowLayout(FlowLayout.RIGHT));
 		
 		JButton resetButton =  new JButton("Reset");
@@ -131,6 +152,10 @@ public abstract class AlgorithmFramework implements AddOn{
 		cancelButton.addActionListener(actionEvent -> cancel());
 		buttonPanel.add(cancelButton);
 		
+		JButton plottButton =  new JButton("Plott");
+		plottButton.addActionListener(actionEvent -> plott());
+		buttonPanel.add(plottButton);
+		
 		JButton fitnessButton =  new JButton("Fitness");
 		fitnessButton.setToolTipText("Fitness for the current state.");
 		fitnessButton.addActionListener(actionEvent -> fitness());
@@ -150,6 +175,93 @@ public abstract class AlgorithmFramework implements AddOn{
 	}
 	
 	
+	
+	//ParameterImports
+	
+	//int
+	protected void addIntParameter(String parameterName, int parameterValue, IntConsumer setter) {
+		this.addIntParameter(parameterName, parameterValue, setter, Integer.MIN_VALUE, Integer.MAX_VALUE);
+	}
+	
+	protected void addIntParameter(String parameterName, int parameterValue, IntConsumer setter, int parameterMinValue) {
+		this.addIntParameter(parameterName, parameterValue, setter, parameterMinValue, Integer.MAX_VALUE);
+	}
+	
+	protected void addIntParameter(String parameterName, int parameterValue, IntConsumer setter, int parameterMinValue, int parameterMaxValue) {
+		JPanel singleParameterPanel = new JPanel();
+		singleParameterPanel.setLayout(new BoxLayout(singleParameterPanel, BoxLayout.LINE_AXIS));
+		singleParameterPanel.setAlignmentX(0.0f);
+		singleParameterPanel.add(new JLabel(parameterName + ": "));
+		singleParameterPanel.add(Box.createHorizontalGlue());
+		NumberFormat format = NumberFormat.getIntegerInstance();
+		format.setGroupingUsed(false);
+		format.setParseIntegerOnly(true);
+		NumberFormatter integerFormatter = new NumberFormatter(format);
+		integerFormatter.setMinimum(parameterMinValue);
+		integerFormatter.setMaximum(parameterMaxValue);
+		integerFormatter.setCommitsOnValidEdit(true);
+		JFormattedTextField singleParameterTextField = new  JFormattedTextField(integerFormatter);
+		singleParameterTextField.setValue(parameterValue);
+		String minValue = (parameterMinValue == Integer.MIN_VALUE)?"Integer.MIN_VALUE":String.valueOf(parameterMinValue);
+		String maxValue = (parameterMaxValue == Integer.MAX_VALUE)?"Integer.MAX_VALUE":String.valueOf(parameterMaxValue);
+		singleParameterTextField.setToolTipText("Only integer \u2208 [" + minValue + "," + maxValue + "]");
+		singleParameterTextField.addPropertyChangeListener(actionEvent -> setter.accept(Integer.parseInt(singleParameterTextField.getValue().toString())));
+		singleParameterTextField.setMaximumSize(new Dimension(200, 30));
+		singleParameterTextField.setPreferredSize(new Dimension(200, 30));
+		singleParameterPanel.add(singleParameterTextField);
+		borderPanel.add(singleParameterPanel);
+	}
+	
+	
+	//double
+	protected void addDoubleParameter(String parameterName, double parameterValue, DoubleConsumer setter) {
+		this.addDoubleParameter(parameterName, parameterValue, setter, Double.MIN_VALUE, Double.MAX_VALUE);
+	}
+	
+	
+	protected void addDoubleParameter(String parameterName, double parameterValue, DoubleConsumer setter, double parameterMinValue) {
+		this.addDoubleParameter(parameterName, parameterValue, setter, parameterMinValue, Double.MAX_VALUE);
+	}
+	
+	
+	protected void addDoubleParameter(String parameterName, double parameterValue, DoubleConsumer setter, double parameterMinValue, double parameterMaxValue) {
+		JPanel singleParameterPanel = new JPanel();
+		singleParameterPanel.setLayout(new BoxLayout(singleParameterPanel, BoxLayout.LINE_AXIS));
+		singleParameterPanel.setAlignmentX(0.0f);
+		singleParameterPanel.add(new JLabel(parameterName + ": "));
+		singleParameterPanel.add(Box.createHorizontalGlue());
+		NumberFormat doubleFormat = NumberFormat.getNumberInstance(Locale.US);
+		doubleFormat.setMinimumFractionDigits(1);
+		doubleFormat.setMaximumFractionDigits(10);
+		doubleFormat.setRoundingMode(RoundingMode.HALF_UP);
+		NumberFormatter doubleFormatter = new NumberFormatter(doubleFormat);
+		doubleFormatter.setMinimum(parameterMinValue);
+		doubleFormatter.setMaximum(parameterMaxValue);
+		JFormattedTextField singleParameterTextField = new  JFormattedTextField(doubleFormatter);
+		singleParameterTextField.setValue(parameterValue);
+		String minValue = (parameterMinValue == Double.MIN_VALUE)?"Double.MIN_VALUE":String.valueOf(parameterMinValue);
+		String maxValue = (parameterMaxValue == Double.MAX_VALUE)?"Double.MAX_VALUE":String.valueOf(parameterMaxValue);
+		singleParameterTextField.setToolTipText("Only double \u2208 [" + minValue + "," + maxValue + "]");
+		singleParameterTextField.addPropertyChangeListener(actionEvent -> setter.accept(Double.parseDouble(singleParameterTextField.getValue().toString())));
+		singleParameterTextField.setMaximumSize(new Dimension(200, 30));
+		singleParameterTextField.setPreferredSize(new Dimension(200, 30));
+		singleParameterPanel.add(singleParameterTextField);
+		borderPanel.add(singleParameterPanel);
+	}
+	//boolean
+	protected void addBooleanParameter(String parameterName, boolean parameterValue, Consumer<Boolean> setter){
+		JPanel singleParameterPanel = new JPanel();
+		singleParameterPanel.setLayout(new BoxLayout(singleParameterPanel, BoxLayout.LINE_AXIS));
+		singleParameterPanel.setAlignmentX(0.0f);
+		singleParameterPanel.add(new JLabel(parameterName + ": "));
+		singleParameterPanel.add(Box.createHorizontalGlue());
+		JCheckBox useGroupNodeCheckBox = new JCheckBox();
+		useGroupNodeCheckBox.setSelected(parameterValue);
+		useGroupNodeCheckBox.addActionListener(actionEvent -> setter.accept(useGroupNodeCheckBox.isSelected()));
+		singleParameterPanel.add(useGroupNodeCheckBox);
+		borderPanel.add(singleParameterPanel);
+	}
+	
 
 	private void startTimer(){
 		startTime = System.currentTimeMillis();
@@ -159,7 +271,14 @@ public abstract class AlgorithmFramework implements AddOn{
 		console.println("Execution Time of Algo in Milliseconds:" + elapsedMilliSeconds);
 	}
 	
-	
+	private void plott() {
+		if(db!=null) {
+			console.println("Plott..");
+			printer.print("");
+		}else {
+			console.println("No run inistialized.");
+		}
+	}
 	
 	
 	private void cancel() {
@@ -394,7 +513,7 @@ public abstract class AlgorithmFramework implements AddOn{
 		public RunPrinter(String filename,  boolean append){
 			this.append = append;
 			fileChooser.setCurrentDirectory(new File(System.getProperty("user.dir")));
-		    fileChooser.setSelectedFile(new File(filename));
+			setFilename(filename);
 		}
 		//public methods
 		public void enableAppend(boolean enable) {

+ 12 - 3
src/exampleAlgorithms/AcoAlgorithm2.java

@@ -9,7 +9,6 @@ import javax.swing.JPanel;
 
 import api.AlgorithmFramework;
 import ui.model.DecoratedState;
-import ui.view.Console;
 
 public class AcoAlgorithm2 extends AlgorithmFramework{
 	
@@ -28,7 +27,14 @@ public class AcoAlgorithm2 extends AlgorithmFramework{
 	
 	
 	
-	
+	public AcoAlgorithm2() {
+		super();
+		addIntParameter("Population", popsize, intValue -> popsize = intValue, 1);
+		addIntParameter("maxGenerations", maxGenerations, intValue -> maxGenerations = intValue, 1);
+		addDoubleParameter("Vaporization", p, doubleValue -> p = doubleValue, 0.0, 1.0);
+		addDoubleParameter("FactorReset", convergenceFactorReset, doubleValue -> convergenceFactorReset = doubleValue, 0.0, 1.0);
+		addBooleanParameter("moreInformation", moreInformation, booleanValue -> moreInformation = booleanValue);
+	}
 	
 	
 	
@@ -42,9 +48,12 @@ public class AcoAlgorithm2 extends AlgorithmFramework{
 	      newFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
 	}
 
+	
+	
+	
 	@Override
 	protected double evaluateState(DecoratedState actualstate) {
-		return PSOAlgorithm.getFitnessValueForState(actualstate);
+		return Evaluation.getFitnessValueForState(actualstate);
 	}
 
 

+ 115 - 0
src/exampleAlgorithms/Evaluation.java

@@ -0,0 +1,115 @@
+package exampleAlgorithms;
+
+import classes.HolonObject;
+import ui.model.DecoratedNetwork;
+import ui.model.DecoratedState;
+import ui.model.DecoratedHolonObject.HolonObjectState;
+
+public class Evaluation {
+	
+	/**
+	 * Calculate the Fitness(Penelty) Value for a state (alias the calculated Position).
+	 * TODO: Make me better Rolf.
+	 * @param state
+	 * @return
+	 */
+	public static double getFitnessValueForState(DecoratedState state) {
+		double fitness = 0.0;
+		double nw_fitness =0.0;
+		double object_fitness = 0.0;
+		
+		// calculate network_fitness
+		for(DecoratedNetwork net : state.getNetworkList()) {
+			float production = net.getSupplierList().stream().map(supplier -> supplier.getEnergyToSupplyNetwork()).reduce(0.0f, (a, b) -> a + b);
+			float consumption = net.getConsumerList().stream().map(con -> con.getEnergyNeededFromNetwork()).reduce(0.0f, (a, b) -> a + b);
+			nw_fitness += Math.abs((production - consumption)/100); //Energy is now everywhere positive
+		}
+		
+		// calculate object_fitness
+		for(DecoratedNetwork net : state.getNetworkList()) {
+			object_fitness += net.getConsumerList().stream().map(con -> holonObjectSupplyPenaltyFunction(con.getSupplyBarPercentage()) + inactiveHolonElementPenalty(con.getModel())).reduce(0.0, (a, b) -> (a + b));
+			//warum war das im network fitness und nicht hier im Object fitness??
+			object_fitness += net.getConsumerList().stream().map(con -> StateToDouble(con.getState())).reduce(0.0, (a,b) -> (a+b));
+			//System.out.console.println("objectfitness for statestuff: " + object_fitness);
+			//object_fitness += net.getPassivNoEnergyList().stream().map(con -> 1000.0).reduce(0.0, (a, b) -> (a + b));
+			object_fitness += net.getPassivNoEnergyList().stream().map(sup -> inactiveHolonElementPenalty(sup.getModel())).reduce(0.0, (a, b) -> (a + b));
+			object_fitness += net.getSupplierList().stream().map(sup -> inactiveHolonElementPenalty(sup.getModel())).reduce(0.0, (a, b) -> (a + b));
+			object_fitness += net.getConsumerSelfSuppliedList().stream().map(con -> inactiveHolonElementPenalty(con.getModel())).reduce(0.0, (a, b) -> (a + b));
+		}
+		fitness = nw_fitness + object_fitness;
+		return fitness;
+	}
+
+	
+	/**
+	 * Untouched:
+	 * Function that returns the fitness depending on the number of elements deactivated in a single holon object
+	 * @param obj Holon Object that contains Holon Elements
+	 * @return fitness value for that object depending on the number of deactivated holon elements
+	 */
+	private static double inactiveHolonElementPenalty(HolonObject obj) {
+		float result = 0;
+		int activeElements = obj.getNumberOfActiveElements();
+		int maxElements = obj.getElements().size();
+		
+		//result = (float) Math.pow((maxElements -activeElements),2)*10;
+		result = (float) Math.pow(5, 4* ( (float) maxElements - (float) activeElements)/ (float) maxElements) - 1;
+		//System.out.console.println("max: " + maxElements + " active: " + activeElements + " results in penalty: " + result);
+	return result;
+		
+	}
+	/**
+	 * Untouched:
+	 * Calculates a penalty value based on the HOs current supply percentage
+	 * @param supplyPercentage
+	 * @return
+	 */
+	private static double holonObjectSupplyPenaltyFunction(float supplyPercentage) {
+		double result = 0;
+		/*if(supplyPercentage == 1)
+			return result;
+		else if(supplyPercentage < 1 && supplyPercentage >= 0.25) // undersupplied inbetween 25% and 100%
+			result = (float) Math.pow(1/supplyPercentage, 2);
+		else if (supplyPercentage < 0.25) //undersupplied with less than 25%
+			result = (float) Math.pow(1/supplyPercentage,2);
+		else if (supplyPercentage < 1.25)  //Oversupplied less than 25%
+			result = (float) Math.pow(supplyPercentage,3) ;
+		else result = (float) Math.pow(supplyPercentage,4); //Oversupplied more than 25%
+		
+		
+		if(Float.isInfinite(result) || Float.isNaN(result))
+			result = 1000;
+	*/
+		if(supplyPercentage <= 1.0) {
+			result = Math.pow(5,((100 - (supplyPercentage*100))/50 + 2)) - Math.pow(5, 2);
+		}
+		else {
+			result = Math.pow(6,((100 - (supplyPercentage*100))/50 + 2)) - Math.pow(6, 2);
+		}
+		
+		return result;
+	}
+	/**
+	 * If you want to get in touch with a reliable state? Working function not in use currently.
+	 * @param state
+	 * @return
+	 */
+	private static double StateToDouble(HolonObjectState state) {
+		switch (state) {
+		case NOT_SUPPLIED:
+			return 150.0;
+		case NO_ENERGY:
+			return 150.0;
+		case OVER_SUPPLIED:
+			return 100.0;
+		case PARTIALLY_SUPPLIED:
+			return 100.0;
+		case PRODUCER:
+			return 0;
+		case SUPPLIED:
+			return 0;
+		default:
+			return 0;
+		}
+	}
+}

+ 1 - 1
src/exampleAlgorithms/GaAlgorithm.java

@@ -73,6 +73,7 @@ public class GaAlgorithm implements AddOn {
 		private double mutateProbabilityInterval = 0.01;
 		private double maxMutationPercent = 0.01;
 		private int rounds = 2;
+		private boolean moreInformation = false;
 		
 		
 		
@@ -80,7 +81,6 @@ public class GaAlgorithm implements AddOn {
 		private boolean useGroupNode = false;
 		private DecoratedGroupNode dGroupNode = null;
 		private boolean cancel = false;
-		private boolean moreInformation = false;
 		private boolean append = false;
 
 		//Parameter defined by Algo

+ 234 - 0
src/exampleAlgorithms/GaAlgorithm2.java

@@ -0,0 +1,234 @@
+package exampleAlgorithms;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.ListIterator;
+import java.util.TreeSet;
+
+import javax.swing.JFrame;
+
+import api.AlgorithmFramework;
+import ui.model.DecoratedState;
+
+public class GaAlgorithm2 extends AlgorithmFramework{
+
+	/**
+	 * Should be even.
+	 */
+	private int popsize = 20;
+	private int maxGenerations = 100;
+	private double tournamentSize = 2.0;
+	private double fixedSwapProbability = 0.02;
+	private boolean useFixedSpawProbability = false;
+	private double fixedMutateProbability = 0.02;
+	private boolean useFixedMutateProbability = false;
+	private boolean useIntervalMutation = true;
+	private double mutateProbabilityInterval = 0.01;
+	private double maxMutationPercent = 0.01;
+	private boolean moreInformation = false;
+	
+	
+	public GaAlgorithm2() {
+		super();
+		addIntParameter("popsize", popsize, intValue -> popsize = intValue, 1);
+		addIntParameter("maxGenerations", maxGenerations, intValue -> maxGenerations = intValue, 1);
+		addDoubleParameter("tournamentSize", tournamentSize, doubleValue -> tournamentSize = doubleValue, 1.0);
+		addDoubleParameter("fixedSwapProbability", fixedSwapProbability, doubleValue -> fixedSwapProbability = doubleValue, 0.0, 1.0);
+		addBooleanParameter("useFixedSpawProbability", useFixedSpawProbability, booleanValue -> useFixedSpawProbability = booleanValue);
+		addDoubleParameter("fixedMutateProbability", fixedMutateProbability, doubleValue -> fixedMutateProbability = doubleValue, 0.0, 1.0);
+		addBooleanParameter("useFixedMutateProbability", useFixedMutateProbability, booleanValue -> useFixedMutateProbability = booleanValue);
+		addBooleanParameter("useIntervalMutation", useIntervalMutation, booleanValue -> useIntervalMutation = booleanValue);
+		addDoubleParameter("mutateProbabilityInterval", mutateProbabilityInterval, doubleValue -> mutateProbabilityInterval = doubleValue, 0.0, 1.0);
+		addDoubleParameter("maxMutationPercent", maxMutationPercent, doubleValue -> maxMutationPercent = doubleValue, 0.0, 1.0);
+		addBooleanParameter("moreInformation", moreInformation, booleanValue -> moreInformation = booleanValue);
+	}
+	
+	public static void main(String[] args)
+	{
+	      JFrame newFrame = new JFrame("exampleWindow");
+	      GaAlgorithm2 instance = new GaAlgorithm2();
+	      newFrame.setContentPane(instance.getPanel());
+	      newFrame.pack();
+	      newFrame.setVisible(true);
+	      newFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
+	}
+	
+	@Override
+	protected double evaluateState(DecoratedState actualstate) {
+		return Evaluation.getFitnessValueForState(actualstate);
+	}
+
+
+	@Override
+	protected int getProgressBarMaxCount() {
+		return this.maxGenerations * this.popsize * this.rounds + rounds;
+	}
+	
+	@Override
+	protected Individual executeAlgo() {
+		Individual best = new Individual();
+		best.position = extractPositionAndAccess();
+		if(moreInformation)console.println("Bit-Array_length: " + best.position.size());
+		best.fitness = evaluatePosition(best.position);
+		List<Double> runList = new ArrayList<Double>();
+		runList.add(best.fitness);
+		console.print("Start with: " + best.fitness);
+		if(moreInformation)console.println("");
+		int problemSize = best.position.size();
+		List<Individual> population = initPopuluationRandom(problemSize, best);
+		if(moreInformation)console.println("Size To Test:" + population.size());
+		for(int generation = 0; generation< maxGenerations; generation++) {
+			if(moreInformation)console.println("Generation" + generation + " start with Fitness: " + best.fitness);
+			for(Individual i : population) {
+				i.fitness = evaluatePosition(i.position);
+				if(moreInformation)console.println("Fitness" + i.fitness);
+				if(i.fitness < best.fitness) best = i;
+				
+			}
+			runList.add(best.fitness);
+			List<Individual> childList = new ArrayList<Individual>();
+			for(int k = 0; k<popsize/2; k++) {
+				Individual parentA = selectAParent(population, popsize);
+				Individual parentB = selectAParent(population, popsize);
+				Individual childA = new Individual(parentA);
+				Individual childB = new Individual(parentB);
+				crossover(childA, childB, problemSize);
+				if(useIntervalMutation)mutateInterval(childA, problemSize);else mutate(childA, problemSize);
+				if(useIntervalMutation)mutateInterval(childB, problemSize);else mutate(childB, problemSize);
+				childList.add(childA);
+				childList.add(childB);
+			}
+			population = childList;
+			if(moreInformation)console.println("________________");
+			if(cancel)return null;
+		}
+		
+		
+		console.println("   End with:" + best.fitness);
+		return best;
+	}
+	/**
+	 * Algorithm 22 Bit-Flip Mutation.
+	 * 
+	 */
+	private void mutate(Individual child, int problemSize) {
+		double probability = (this.useFixedMutateProbability) ? this.fixedMutateProbability : 1.0/(double)problemSize;
+		ListIterator<Boolean> iter = child.position.listIterator();
+		while(iter.hasNext()) {
+			boolean boolValue = iter.next();
+			if(Random.nextDouble() <=  probability) {
+				iter.set(!boolValue);
+			}
+		}
+	}
+	
+	/**
+	 * Algorithm rolf
+	 * 
+	 */
+	private void mutateInterval(Individual child, int problemSize) {
+		//If not mutate skip
+		if(Random.nextDouble() >  this.mutateProbabilityInterval) {
+			return;
+		}
+		//println("problemSize:" + problemSize + "    maxMutationPercent:" + maxMutationPercent);
+		int maximumAmountOfMutatedBits = Math.max(1, (int)Math.round(((double) problemSize) * this.maxMutationPercent));
+		int randomUniformAmountOfMutatedValues = Random.nextIntegerInRange(1,maximumAmountOfMutatedBits + 1);
+		
+		//println("max:" + maximumAmountOfMutatedBits + "   actual:" + randomUniformAmountOfMutatedValues);
+		TreeSet<Integer> mutationLocation = new TreeSet<Integer>(); //sortedSet
+		//Choose the location to mutate
+		for(int i = 0; i< randomUniformAmountOfMutatedValues; i++) {
+			boolean success = mutationLocation.add(Random.nextIntegerInRange(0, problemSize));
+			if(!success) i--; //can be add up to some series long loops if maximumAmountOfMutatedBits get closed to problemsize.
+		}
+		//println("Set:" + mutationLocation);
+		ListIterator<Boolean> iter = child.position.listIterator();
+		if(mutationLocation.isEmpty()) return;
+		int firstindex = mutationLocation.pollFirst();
+		while(iter.hasNext()) {
+			int index = iter.nextIndex();
+			boolean boolValue = iter.next();
+			if(index == firstindex) {
+				iter.set(!boolValue);
+				//println("changed Value["+ index +"]");
+				if(mutationLocation.isEmpty()) break;
+				firstindex = mutationLocation.pollFirst();
+			}
+		}
+	}
+	
+	
+	
+	
+	/** 
+	 * Algorithm 25 Uniform Crossover.
+	 * Probability is set to 1/Problemsize when not changed.
+	 */
+	private void crossover(Individual childA, Individual childB, int problemSize) {
+		double probability = (this.useFixedSpawProbability) ? this.fixedSwapProbability : 1.0/(double)problemSize;
+		ListIterator<Boolean> iterA = childA.position.listIterator();
+		ListIterator<Boolean> iterB = childB.position.listIterator();
+		for(int i= 0; i < problemSize; i++) {
+			boolean boolA = iterA.next();
+			boolean boolB = iterB.next();
+			if(Random.nextDouble() <=  probability ) {
+				//Swap 
+				iterA.set(boolB);
+				iterB.set(boolA);
+			}
+		}
+	}
+	/**
+	 * Algorithm 32 Tournament Selection.
+	 * The fitnessValues are calculated for the Population List.
+	 * PseudoCode
+	 */
+	private Individual selectAParent(List<Individual> population,int popsize) {
+		Individual tournamentBest = population.get(Random.nextIntegerInRange(0, popsize));
+		double participants;
+		for(participants = tournamentSize ; participants >= 2; participants -= 1.0) {
+			Individual next = population.get(Random.nextIntegerInRange(0, popsize));
+			if(next.fitness < tournamentBest.fitness) tournamentBest = next;
+		}
+		//if tournament size is not a whole number like 2.5 or 3.6
+		//the remaining part is the chance to fight another time; 2.7 -> 70% chance to fight a second time
+		if( participants > 1) {		
+			if(Random.nextDouble() < participants - 1.0) {
+				//println("Chance to find a match");
+				Individual next = population.get(Random.nextIntegerInRange(0, popsize));
+				if(next.fitness < tournamentBest.fitness) tournamentBest = next;
+			}
+		}
+		return tournamentBest;
+	}
+	/**
+	 * Initialize the Population with Individuals that have a random Position.
+	 */
+	private List<Individual> initPopuluationRandom(int problemSize, Individual startIndidual){
+		List<Individual> population =  new ArrayList<Individual>();
+		for(int i = 0; i < popsize -1; i++) {
+			population.add(createRandomIndividualWithoutFitness(problemSize));
+		}
+		//Add Start Position
+		population.add(new Individual(startIndidual));
+		return population;
+	}
+	
+	
+	
+	/**
+	 * Algorithm 21 The BooleanVeator initialization.
+	 * @param problemSize
+	 * @return
+	 */
+	private Individual createRandomIndividualWithoutFitness(int problemSize) {
+		//create Random Individual Without Fitness
+		Individual result = new Individual();
+		result.position = new ArrayList<Boolean>();
+		for (int index = 0; index < problemSize; index++){
+			result.position.add(Random.nextBoolean());
+		}
+		return result;
+	}
+}

+ 1 - 1
src/exampleAlgorithms/PSOAlgorithm.java

@@ -73,6 +73,7 @@ public class PSOAlgorithm implements AddOn {
 	private double maxMutationPercent = 0.01;
 	
 	
+	private double c1, c2, w;
 	
 	
 	//Settings For GroupNode using and plotting
@@ -83,7 +84,6 @@ public class PSOAlgorithm implements AddOn {
 	//Parameter defined by Algo
 	private HashMap<Integer, AccessWrapper> access;
 	LinkedList<List<Boolean>> resetChain = new LinkedList<List<Boolean>>();
-	private double c1, c2, w;
 	private RunDataBase db;
 	
 	//Parameter for Plotting (Default Directory in Constructor)

+ 323 - 0
src/exampleAlgorithms/PsoAlgorithm2.java

@@ -0,0 +1,323 @@
+package exampleAlgorithms;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.TreeSet;
+import java.util.stream.Collectors;
+
+import javax.swing.JFrame;
+
+import api.AlgorithmFramework;
+import ui.model.DecoratedState;
+
+public class PsoAlgorithm2 extends AlgorithmFramework{
+	//Parameter for Algo with default Values:
+	private int swarmSize = 20; 
+	private int maxIterations = 100; 
+	private double limit = 0.01; 
+	private double dependency = 2.07; 
+	private int mutationInterval = 1;
+	private boolean useIntervalMutation = true;
+	private double mutateProbabilityInterval = 0.01;
+	private double maxMutationPercent = 0.01;
+	private double c1, c2, w;
+	
+	
+	
+	public static void main(String[] args)
+	{
+	      JFrame newFrame = new JFrame("exampleWindow");
+	      PsoAlgorithm2 instance = new PsoAlgorithm2();
+	      newFrame.setContentPane(instance.getPanel());
+	      newFrame.pack();
+	      newFrame.setVisible(true);
+	      newFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
+	}
+	
+	
+	public PsoAlgorithm2() {
+		super();
+		addIntParameter("swarmSize", swarmSize, intValue -> swarmSize = intValue, 1);
+		addIntParameter("maxIterations", maxIterations, intValue -> maxIterations = intValue, 1);
+		addIntParameter("mutationInterval", mutationInterval, intValue -> mutationInterval = intValue, 0);
+		addDoubleParameter("dependency", dependency, doubleValue -> dependency = doubleValue, 2.001, 2.4);
+		addDoubleParameter("limit", limit, doubleValue -> limit = doubleValue, 0.0, 1.0);
+		addBooleanParameter("useIntervalMutation", useIntervalMutation, booleanValue -> useIntervalMutation = booleanValue);
+		addDoubleParameter("mutateProbabilityInterval", mutateProbabilityInterval, doubleValue -> mutateProbabilityInterval = doubleValue, 0.0, 1.0);
+		addDoubleParameter("maxMutationPercent", maxMutationPercent, doubleValue -> maxMutationPercent = doubleValue, 0.0, 1.0);
+	}
+	
+	@Override
+	protected double evaluateState(DecoratedState actualstate) {
+		return Evaluation.getFitnessValueForState(actualstate);
+	}
+
+
+	@Override
+	protected int getProgressBarMaxCount() {
+		return swarmSize * (maxIterations + 1)* rounds + rounds;
+	}
+	/**
+	 *  <p>Algo from Paper:</p><font size="3"><pre>
+	 *  
+	 *  Begin
+	 *  	t = 0; {t: generation index}
+	 *  	initialize particles x<sub>p,i,j</sub>(t);
+	 *  	evaluation x<sub>p,i,j</sub>(t);
+	 *  	while (termination condition &ne; true) do
+	 *  		v<sub>i,j</sub>(t) = update v<sub>i,j</sub>(t); {by Eq. (6)}
+	 *  		x<sub>g,i,j</sub>(t) = update x<sub>g,i,j</sub>(t); {by Eq. (7)}
+	 *  		x<sub>g,i,j</sub>(t) = mutation x<sub>g,i,j</sub>(t); {by Eq. (11)}
+	 *  		x<sub>p,i,j</sub>(t) = decode x<sub>g,i,j</sub>(t); {by Eqs. (8) and (9)}
+	 *  		evaluate x<sub>p,i,j</sub>(t);
+	 *  		t = t + 1;
+	 *  	end while
+	 *  End</pre></font>
+	 *  <p>with:</p><font size="3">
+	 *  
+	 *  x<sub>g,i,j</sub>: genotype ->genetic information -> in continuous space<br>
+	 *  x<sub>p,i,j</sub>: phenotype -> observable characteristics-> in binary space<br>
+	 *  X<sub>g,max</sub>: is the Maximum here set to 4.<br>
+	 *  Eq. (6):v<sub>i,j</sub>(t + 1) = wv<sub>i,j</sub>+c<sub>1</sub>R<sub>1</sub>(P<sub>best,i,j</sub>-x<sub>p,i,j</sub>(t))+c<sub>2</sub>R<sub>2</sub>(g<sub>best,i,j</sub>-x<sub>p,i,j</sub>(t))<br>
+	 *  Eq. (7):x<sub>g,i,j</sub>(t + 1) = x<sub>g,i,j</sub>(t) + v<sub>i,j</sub>(t + 1)<br>
+	 *  Eq. (11):<b>if(</b>rand()&lt;r<sub>mu</sub><b>)then</b> x<sub>g,i,j</sub>(t + 1) = -x<sub>g,i,j</sub>(t + 1)<br>
+	 *  Eq. (8):x<sub>p,i,j</sub>(t + 1) = <b>(</b>rand() &lt; S(x<sub>g,i,j</sub>(t + 1))<b>) ?</b> 1 <b>:</b> 0<br>
+	 *  Eq. (9) Sigmoid:S(x<sub>g,i,j</sub>(t + 1)) := 1/(1 + e<sup>-x<sub>g,i,j</sub>(t + 1)</sup>)<br></font>
+	 *  <p>Parameter:</p>
+	 *  w inertia, calculated from phi(Variable:{@link #dependency})<br>
+	 *  c1:	influence, calculated from phi(Variable:{@link #dependency}) <br>
+	 *  c2:	influence, calculated from phi(Variable:{@link #dependency})<br>
+	 *  r<sub>mu</sub>: probability that the proposed operation is conducted defined by limit(Variable:{@link #limit})<br>
+	 *  
+	 *  
+	 */
+	@Override
+	protected Individual executeAlgo() {
+		initDependentParameter();
+		Individual globalBest = new Individual();
+		globalBest.position = extractPositionAndAccess();
+		globalBest.fitness = evaluatePosition(globalBest.position);
+		console.println("Start Value:" + globalBest.fitness);
+		int dimensions = globalBest.position.size();
+		List<Particle> swarm= initializeParticles(dimensions);
+		List<Double> runList = new ArrayList<Double>();
+		runList.add(globalBest.fitness);
+		evaluation(globalBest, swarm);
+		runList.add(globalBest.fitness);
+		for (int iteration = 0; iteration < maxIterations ; iteration++) {
+			int mutationAllowed = iteration % mutationInterval;
+			for (int particleNumber = 0; particleNumber < swarmSize; particleNumber++) {
+				Particle particle = swarm.get(particleNumber);		
+				
+				if(this.useIntervalMutation) {
+					boolean allowMutation = (Random.nextDouble() <  this.mutateProbabilityInterval);
+					TreeSet<Integer> mutationLocation = null;
+					if(allowMutation)mutationLocation = locationsToMutate(dimensions);
+					for(int index = 0; index < dimensions; index++) {
+						updateVelocity(particle, index, globalBest);
+						updateGenotype(particle, index);
+						if(allowMutation &&mutationAllowed == 0 && iteration != 0 && mutationLocation.contains(index))mutation(particle, index);
+						decode(particle, index);
+					}
+				}else {					
+					for(int index = 0; index < dimensions; index++) {
+						updateVelocity(particle, index, globalBest);
+						updateGenotype(particle, index);
+						if(mutationAllowed == 0 && iteration != 0)mutation(particle, index);
+						decode(particle, index);
+					}
+				}
+			}
+			if(cancel)return null;
+			evaluation(globalBest, swarm);
+			runList.add(globalBest.fitness);
+		}
+		console.println(" End Value:" + globalBest.fitness);
+		db.insertNewRun(runList);
+		return globalBest;
+	}
+	/**
+	 * 
+	 * @param j maximum index of position in the particle
+	 * @return
+	 */
+	private List<Particle> initializeParticles(int j) {
+		List<Particle> swarm = new ArrayList<Particle>();
+		//Create The Particle
+		for (int particleNumber = 0; particleNumber < swarmSize; particleNumber++){
+			//Create a Random position
+			List<Boolean> aRandomPosition = new ArrayList<Boolean>();
+			for (int index = 0; index < j; index++){
+				aRandomPosition.add(Random.nextBoolean());
+			}
+			swarm.add(new Particle(aRandomPosition));
+		}
+		return swarm;
+	}
+	/**
+	 * Calculate w, c1, c2
+	 */
+	private void initDependentParameter() {
+		w = 1.0 / (dependency - 1 + Math.sqrt(dependency * dependency - 2 * dependency));
+		c1 = c2 = dependency * w;
+	}
+	/**
+	 * Evaluate each particle and update the global Best position;
+	 * @param globalBest
+	 * @param swarm
+	 */
+	private void evaluation(Individual globalBest, List<Particle> swarm) {
+		for(Particle p: swarm) {
+			double localEvaluationValue = evaluatePosition(p.xPhenotype);
+			p.checkNewEvaluationValue(localEvaluationValue);
+			if(localEvaluationValue < globalBest.fitness) {
+				globalBest.fitness = localEvaluationValue;
+				globalBest.position = p.localBest.position;
+			}
+		}
+	}
+	/**
+	 * 	Eq. (6):v<sub>i,j</sub>(t + 1) = wv<sub>i,j</sub>+c<sub>1</sub>R<sub>1</sub>(P<sub>best,i,j</sub>-x<sub>p,i,j</sub>(t))+c<sub>2</sub>R<sub>2</sub>(g<sub>best,i,j</sub>-x<sub>p,i,j</sub>(t))<br>
+	 * @param particle
+	 * @param index
+	 * @param globalBest
+	 */
+	private void updateVelocity(Particle particle, int index, Individual globalBest) {
+		double r1 = Random.nextDouble();
+		double r2 =	Random.nextDouble();
+		double posValue = particle.xPhenotype.get(index)?1.0:0.0;
+		particle.velocity.set(index, clamp(w*particle.velocity.get(index) + c1*r1*((particle.localBest.position.get(index)?1.0:0.0)  - posValue) + c2*r2*((globalBest.position.get(index)?1.0:0.0)- posValue)) );
+	}
+	/**
+	 * Eq. (7):x<sub>g,i,j</sub>(t + 1) = x<sub>g,i,j</sub>(t) + v<sub>i,j</sub>(t + 1)<br>
+	 * @param particle
+	 * @param index
+	 */
+	private void updateGenotype(Particle particle, int index) {
+		particle.xGenotype.set(index, clamp(particle.xGenotype.get(index) + particle.velocity.get(index)));
+	}
+	/**
+	 * Eq. (11):<b>if(</b>rand()&lt;r<sub>mu</sub><b>)then</b> x<sub>g,i,j</sub>(t + 1) = -x<sub>g,i,j</sub>(t + 1)<br>
+	 * @param particle
+	 * @param index
+	 */
+	private void mutation(Particle particle, int index) {
+		if(Random.nextDouble() < limit) particle.xGenotype.set(index, -particle.xGenotype.get(index));
+	}
+	/**
+	 * Eq. (8):x<sub>p,i,j</sub>(t + 1) = <b>(</b>rand() &lt; S(x<sub>g,i,j</sub>(t + 1))<b>) ?</b> 1 <b>:</b> 0<br>
+	 * @param particle
+	 * @param index
+	 */
+	private void decode(Particle particle, int index) {
+		particle.xPhenotype.set(index, Random.nextDouble() < Sigmoid(particle.xGenotype.get(index)));
+	}
+	/**
+	 * Eq. (9) Sigmoid:S(x<sub>g,i,j</sub>(t + 1)) := 1/(1 + e<sup>-x<sub>g,i,j</sub>(t + 1)</sup>)<br></font>
+	 * @param value
+	 * @return
+	 */
+	private double Sigmoid(double value) {
+		return 1.0 / (1.0 + Math.exp(-value));
+	}
+
+	/**
+	 * To clamp X<sub>g,j,i</sub> and v<sub>i,j</sub> in Range [-X<sub>g,max</sub>|+X<sub>g,max</sub>] with {X<sub>g,max</sub>= 4}
+	 * @param value
+	 * @return
+	 */
+	private double clamp(double value) {
+		return Math.max(-4.0, Math.min(4.0, value));
+	}
+	private TreeSet<Integer> locationsToMutate(int dimensions) {
+		TreeSet<Integer> mutationLocation = new TreeSet<Integer>(); //sortedSet
+		int maximumAmountOfMutatedBits = Math.max(1, (int)Math.round(((double) dimensions) * this.maxMutationPercent));
+		int randomUniformAmountOfMutatedValues = Random.nextIntegerInRange(1,maximumAmountOfMutatedBits + 1);
+		for(int i = 0; i< randomUniformAmountOfMutatedValues; i++) {
+			boolean success = mutationLocation.add(Random.nextIntegerInRange(0, dimensions));
+			if(!success) i--; //can be add up to some series long loops if maximumAmountOfMutatedBits get closed to problemsize.
+		}
+		//console.println(mutationLocation.toString());
+		return mutationLocation;
+	}
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	
+	/**
+	 * Class to represent a Particle.
+	 */
+	private class Particle{
+		/**
+		 * The velocity of a particle.
+		 */
+		public List<Double> velocity;
+		/**
+		 * The positions genotype.
+		 */
+		public List<Double> xGenotype;
+		/**
+		 * The positions phenotype. Alias the current position.
+		 */
+		public List<Boolean> xPhenotype;
+		
+		public Individual localBest;
+		
+		Particle(List<Boolean> position){
+			this.xPhenotype = position;
+			//Init velocity, xGenotype with 0.0 values.
+			this.velocity = position.stream().map(bool -> 0.0).collect(Collectors.toList());
+			this.xGenotype = position.stream().map(bool -> 0.0).collect(Collectors.toList());
+			localBest = new Individual();
+			localBest.fitness = Double.MAX_VALUE;
+		}
+		public void checkNewEvaluationValue(double newEvaluationValue) {
+			if(newEvaluationValue < localBest.fitness) {
+				localBest.fitness = newEvaluationValue;
+				localBest.position = xPhenotype.stream().map(bool -> bool).collect(Collectors.toList());
+			}
+		}
+		public String toString() {
+			return "Particle with xPhenotype(Position), xGenotype, velocity:[" 
+					+ listToString(xPhenotype) + "],[" + listToString(xGenotype) + "],[" 
+					+ listToString(velocity) + "]";
+		}
+		private <Type> String listToString(List<Type> list) {
+			return list.stream().map(Object::toString).collect(Collectors.joining(", "));
+		}
+		
+	}
+		
+		
+		
+		
+		
+
+}