123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252 |
- package algorithms.geneticAlgorithm.holegGA.Components;
- import java.util.ArrayList;
- 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 algorithms.geneticAlgorithm.Components.GAMutationStrategy;
- import algorithms.geneticAlgorithm.holegGA.GAEdge;
- import algorithms.geneticAlgorithm.holegGA.ParameterArray;
- public class HolegMutation extends GAMutationStrategy<HolegIndividual>{
-
- 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();
- }
-
- public HolegMutation(double prob){
- super(prob);
- }
- @Override
- public HolegIndividual mutateIndividual(HolegIndividual mutant) {
-
- 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:
- removeEdge(mutant);
- break;
- }
-
- }
- return mutant;
- }
- public void removeObject(HolegIndividual mutant, int removeIdx) {
- ArrayList<CpsEdge> connections = new ArrayList<CpsEdge>();
- connections.addAll(mutant.getObjectWithIndex(removeIdx).getConnections());
- for(CpsEdge e : connections){
- e.getA().getConnections().remove(e);
- e.getB().getConnections().remove(e);
- }
- ArrayList<GAEdge> edgesToRemove = new ArrayList<GAEdge>();
- for(GAEdge gE : mutant.getAllEdges()){
- if(gE.aPos == removeIdx || gE.bPos == removeIdx){
- edgesToRemove.add(gE);
- }
- }
- mutant.getAllEdges().removeAll(edgesToRemove);
- mutant.addLogEntry("Object wit ID " + mutant.indexToObjectMap.get(removeIdx).getId() + " removed");
- mutant.removeObject(removeIdx);
- }
- public void changeObject(HolegIndividual mutant, int changeIdx) {
- if(objSpace.size() > 0){
- AbstractCpsObject newObj = null;
- AbstractCpsObject absObj = objSpace.get(rng.nextInt(objSpace.size()));
- newObj = absObj.makeCopy();
-
- AbstractCpsObject oldObject = mutant.getObjectWithIndex(changeIdx);
- for(CpsEdge e : oldObject.getConnections()){
- if(e.getA() == oldObject){
- e.setA(newObj);
- newObj.addConnection(e);
- }else if(e.getB() == oldObject){
- e.setB(newObj);
- newObj.addConnection(e);
- }
- }
- newObj.setId(oldObject.getId());
- newObj.setPosition(oldObject.getPosition());
-
- mutant.indexToObjectMap.put(changeIdx, newObj);
- mutant.addLogEntry("Object with Id " + newObj.getId() + " changed");
- }
- }
- public void removeEdge(HolegIndividual mutant) {
- 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);
- 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.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 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);
- if(changeA){
- 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.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.getAdditionalEdges().remove(toChange);
- }
- }
- }
-
- }
-
- 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;
- }
- }
|