package ui.model; import java.util.ArrayList; import java.util.List; import java.util.stream.Collectors; import classes.HolonElement; import classes.HolonObject; import ui.controller.FlexManager; import ui.model.DecoratedCable.CableState; import ui.model.DecoratedHolonObject.HolonObjectState; import ui.model.Model.FairnessModel; public class DecoratedNetwork { private ArrayList supplierList = new ArrayList(); private ArrayList consumerList = new ArrayList(); private ArrayList consumerSelfSuppliedList = new ArrayList(); private ArrayList passivNoEnergyList = new ArrayList(); private ArrayList decoratedCableList = new ArrayList(); private int timestep; public DecoratedNetwork(MinimumNetwork minimumNetwork, int Iteration, FairnessModel actualFairnessModel, FlexManager flexManager){ this.timestep = Iteration; switch(actualFairnessModel) { case AllEqual: calculateAllEqualNetwork(minimumNetwork, Iteration, flexManager); break; case MininumDemandFirst: default: calculateMinimumDemandFirstNetwork(minimumNetwork, Iteration, flexManager); break; } } //Getter: public ArrayList getSupplierList() { return supplierList; } public ArrayList getConsumerList() { return consumerList; } public ArrayList getConsumerSelfSuppliedList() { return consumerSelfSuppliedList; } public ArrayList getPassivNoEnergyList() { return passivNoEnergyList; } public ArrayList getDecoratedCableList(){ return decoratedCableList; } //Calculations: private void calculateMinimumDemandFirstNetwork(MinimumNetwork minimumNetwork, int Iteration, FlexManager flexManager) { categorize(minimumNetwork, Iteration, flexManager); //Sort SupplierList according to the EnergyToSupplyNetwork maximum first. //Sort ConsumerList according to the MinimumConsumingElementEnergy minimum first. supplierList.sort((Supplier lhs,Supplier rhs) -> -Float.compare(lhs.getEnergyToSupplyNetwork(), rhs.getEnergyToSupplyNetwork())); consumerList.sort((Consumer lhs,Consumer rhs) -> Float.compare(lhs.getMinimumConsumingElementEnergy() , rhs.getMinimumConsumingElementEnergy())); //consumerList.forEach((con) -> System.out.println(con.getMinimumConsumingElementEnergy())); //consumerList.forEach((con) -> System.out.println("AfterSorting" + con)); float energyToSupplyInTheNetwork = supplierList.stream().map(supplier -> supplier.getEnergyToSupplyNetwork() - supplier.getEnergySupplied()).reduce( 0.0f, (a, b) -> a + b); decorateCable(minimumNetwork, energyToSupplyInTheNetwork); outerLoop: for(Consumer con : consumerList) { //gehe Supplier list durch wer ihn supplien kann. for(Supplier sup : supplierList) { float energyRdyToSupply = sup.getEnergyToSupplyNetwork() - sup.getEnergySupplied(); if(energyRdyToSupply == 0.0f) continue; float energyNeededForMinimumConsumingElement=con.getMinimumConsumingElementEnergy()-con.getEnergyFromNetwork(); if(energyNeededForMinimumConsumingElement>energyToSupplyInTheNetwork) { //Dont supply a minimumElement when you cant supply it fully break outerLoop; } if(energyRdyToSupply>=energyNeededForMinimumConsumingElement) { energyToSupplyInTheNetwork -= energyNeededForMinimumConsumingElement; supply(con, sup, energyNeededForMinimumConsumingElement); continue outerLoop; }else { energyToSupplyInTheNetwork -= energyRdyToSupply; supply(con, sup, energyRdyToSupply); } } //No more Energy in the network break; } //consumerList.forEach((con) -> System.out.println("AfterSuppliing MinimumDemand " + con)); //Sort ConsumerList according to the EnergyNeeded to supply fully after minimum Demand First. consumerList.sort((Consumer lhs,Consumer rhs) -> Float.compare(lhs.getEnergyNeededFromNetwork()-lhs.getEnergyFromNetwork() , rhs.getEnergyNeededFromNetwork()-rhs.getEnergyFromNetwork() )); //Supply consumer fully outerLoop: for(Consumer con : consumerList) { //gehe Supplier list durch wer ihn supplien kann. for(Supplier sup : supplierList) { float energyRdyToSupply = sup.getEnergyToSupplyNetwork() - sup.getEnergySupplied(); if(energyRdyToSupply == 0.0f) continue; float energyNeededForFullySupply = con.getEnergyNeededFromNetwork() - con.getEnergyFromNetwork(); if(energyNeededForFullySupply == 0.0f) continue outerLoop; if(energyRdyToSupply>=energyNeededForFullySupply) { supply(con, sup, energyNeededForFullySupply); continue outerLoop; }else { supply(con, sup, energyRdyToSupply); } } //No more Energy in the network break; } //consumerList.forEach((con) -> System.out.println("AfterFullySuplieing" + con)); //If Energy Left Supply all equal //Count EnergyLeft float energyLeft = supplierList.stream().map(supplier -> supplier.getEnergyToSupplyNetwork() - supplier.getEnergySupplied()).reduce( 0.0f, (a, b) -> a + b); //System.out.println("EnergyLeft: " + energyLeft); if(energyLeft > 0.0f && (consumerList.size() + consumerSelfSuppliedList.size() != 0)) { float equalAmountOfEnergyToSupply = energyLeft / ((float)(consumerList.size() + consumerSelfSuppliedList.size())); outerLoop: for(Consumer con : consumerList) { //gehe Supplier list durch wer ihn supplien kann. for(Supplier sup : supplierList) { float energyRdyToSupply = sup.getEnergyToSupplyNetwork() - sup.getEnergySupplied(); if(energyRdyToSupply == 0.0f) continue; float energyNeededToSupplyConsumerTheEqualAmount = equalAmountOfEnergyToSupply +con.getEnergyNeededFromNetwork()- con.getEnergyFromNetwork(); if(energyRdyToSupply>=energyNeededToSupplyConsumerTheEqualAmount) { supply(con, sup, energyNeededToSupplyConsumerTheEqualAmount); continue outerLoop; }else { supply(con, sup, energyRdyToSupply); } } //No more Energy in the network break; } outerLoop: for(Consumer con : consumerSelfSuppliedList) { //gehe Supplier list durch wer ihn supplien kann. for(Supplier sup : supplierList) { float energyRdyToSupply = sup.getEnergyToSupplyNetwork() - sup.getEnergySupplied(); if(energyRdyToSupply == 0.0f) continue; float energyNeededToSupplyConsumerTheEqualAmount = equalAmountOfEnergyToSupply +con.getEnergyNeededFromNetwork()- con.getEnergyFromNetwork(); if(energyRdyToSupply>=energyNeededToSupplyConsumerTheEqualAmount) { supply(con, sup, energyNeededToSupplyConsumerTheEqualAmount); continue outerLoop; }else { supply(con, sup, energyRdyToSupply); } } //No more Energy in the network break; } } //consumerList.forEach((con) -> System.out.println("AfterOverSuppleiing" + con)); //consumerSelfSuppliedList.forEach((con) -> System.out.println("AfterOverSuppleiing" + con)); calculateStates(); } private void decorateCable(MinimumNetwork minimumNetwork, float energyToSupplyInTheNetwork) { //DecoratedCables //Minimum demand first: for(IntermediateCableWithState edge: minimumNetwork.getEdgeList()) { decoratedCableList.add(new DecoratedCable(edge.getModel(), edge.getState(), (edge.getState() == CableState.Working) ? energyToSupplyInTheNetwork : 0.0f)); } } private void calculateAllEqualNetwork(MinimumNetwork minimumNetwork, int Iteration, FlexManager flexManager) { categorize(minimumNetwork, Iteration, flexManager); float energyToSupplyInTheNetwork = supplierList.stream().map(supplier -> supplier.getEnergyToSupplyNetwork() - supplier.getEnergySupplied()).reduce( 0.0f, (a, b) -> a + b); float energyForEachConsumer = (consumerList.size() != 0) ? energyToSupplyInTheNetwork / consumerList.size() : 0.0f; decorateCable(minimumNetwork, energyToSupplyInTheNetwork); //Supply consumer equal outerLoop: for(Consumer con : consumerList) { //gehe Supplier list durch wer ihn supplien kann. float energyNeededForEqualSupply = energyForEachConsumer; for(Supplier sup : supplierList) { float energyRdyToSupply = sup.getEnergyToSupplyNetwork() - sup.getEnergySupplied(); if(energyRdyToSupply == 0.0f) continue; if(energyRdyToSupply>=energyNeededForEqualSupply) { supply(con, sup, energyNeededForEqualSupply); continue outerLoop; }else { supply(con, sup, energyRdyToSupply); energyNeededForEqualSupply -= energyRdyToSupply; } } //No more Energy in the network break; } calculateStates(); } private void calculateStates() { //CalculateStates: supplierList.forEach(sup -> sup.setState(HolonObjectState.PRODUCER)); passivNoEnergyList.forEach(sup -> sup.setState(HolonObjectState.NO_ENERGY)); for(Consumer con : this.consumerList) { setConsumerState(con); } for(Consumer con : this.consumerSelfSuppliedList) { setConsumerState(con); } } private void categorize(MinimumNetwork minimumNetwork, int Iteration, FlexManager flexManager) { //Categorize for(HolonObject hObject: minimumNetwork.getHolonObjectList()) { float energyNeeded = hObject.getEnergyNeededFromConsumingElementsWithFlex(Iteration, flexManager); float energySelfProducing = hObject.getEnergySelfProducingFromProducingElementsWithFlex(Iteration, flexManager); if(energyNeeded < energySelfProducing) { Supplier sup = new Supplier(hObject, energySelfProducing - energyNeeded, energyNeeded); supplierList.add(sup); } else if (energyNeeded > energySelfProducing) { Consumer con = new Consumer(hObject); con.setEnergyNeededFromNetwork(energyNeeded - energySelfProducing); con.setMinimumConsumingElementEnergy(hObject.getMinimumConsumingElementEnergyWithFlex(Iteration, flexManager)); con.setEnergyFromConsumingElemnets(hObject.getEnergyNeededFromConsumingElementsWithFlex(Iteration, flexManager)); con.setEnergySelfSupplied(hObject.getEnergySelfProducingFromProducingElementsWithFlex(Iteration, flexManager)); consumerList.add(con); }else if(energyNeeded == energySelfProducing) { if (energySelfProducing == 0.0f) { Passiv pas = new Passiv(hObject); passivNoEnergyList.add(pas); } else { Consumer con = new Consumer(hObject); con.setEnergyNeededFromNetwork(0.0f); con.setMinimumConsumingElementEnergy(hObject.getMinimumConsumingElementEnergyWithFlex(Iteration, flexManager)); con.setEnergyFromConsumingElemnets(hObject.getEnergyNeededFromConsumingElementsWithFlex(Iteration, flexManager)); con.setEnergySelfSupplied(hObject.getEnergySelfProducingFromProducingElementsWithFlex(Iteration, flexManager)); consumerSelfSuppliedList.add(con); } } } } private void setConsumerState(Consumer con) { if(con.getEnergySelfSupplied() + con.getEnergyFromNetwork() > con.getEnergyFromConsumingElemnets()) { con.setState(HolonObjectState.OVER_SUPPLIED); }else if(con.getEnergySelfSupplied() + con.getEnergyFromNetwork() == con.getEnergyFromConsumingElemnets()) { con.setState(HolonObjectState.SUPPLIED); }else if(con.getEnergySelfSupplied() + con.getEnergyFromNetwork() >= con.getMinimumConsumingElementEnergy()) { con.setState(HolonObjectState.PARTIALLY_SUPPLIED); }else { con.setState(HolonObjectState.NOT_SUPPLIED); } } /** * No Checks. * @param con * @param sup * @param energy */ private void supply(Consumer con, Supplier sup, float energy) { sup.getConsumerList().add(sup.new ConsumerListEntry(con , energy)); sup.setEnergySupplied(sup.getEnergySupplied() + energy); con.getSupplierList().add(con.new SupplierListEntry(sup, energy)); con.setEnergyFromNetwork(con.getEnergyFromNetwork() + energy); } public int getAmountOfActiveElements() { return supplierList.stream().map(object -> object.getModel().getNumberOfActiveElements()).reduce(0, Integer::sum)+ consumerList.stream().map(object -> object.getModel().getNumberOfActiveElements()).reduce(0, Integer::sum)+ consumerSelfSuppliedList.stream().map(object -> object.getModel().getNumberOfActiveElements()).reduce(0, Integer::sum); } public int getAmountOfElements() { return supplierList.stream().map(object -> object.getModel().getNumberOfElements()).reduce(0, Integer::sum)+ consumerList.stream().map(object -> object.getModel().getNumberOfElements()).reduce(0, Integer::sum)+ consumerSelfSuppliedList.stream().map(object -> object.getModel().getNumberOfElements()).reduce(0, Integer::sum); } public int getAmountOfConsumer() { return consumerList.size() + this.consumerSelfSuppliedList.size(); } public int getAmountOfSupplier() { return supplierList.size(); } public int getAmountOfConsumerWithState(HolonObjectState state) { return (int) (consumerList.stream().filter(con -> con.getState() == state).count() + consumerSelfSuppliedList.stream().filter(con -> con.getState() == state).count()); } public int getAmountOfPassiv() { return passivNoEnergyList.size(); } public int getAmountOfHolonObjects() { return getAmountOfConsumer() + getAmountOfSupplier() + getAmountOfPassiv(); } public float getTotalConsumption() { float energy = consumerList.stream().map(con -> con.getEnergyFromConsumingElemnets()).reduce(0.f, Float::sum) + consumerSelfSuppliedList.stream().map(con -> con.getEnergyFromConsumingElemnets()).reduce(0.f, Float::sum); energy += supplierList.stream().map(sup -> sup.getEnergySelfConsuming()).reduce(0.f, Float::sum); return energy; } public float getAverageConsumptionInNetworkForHolonObject(){ return getTotalConsumption() / (float)getAmountOfHolonObjects(); } public float getTotalProduction() { float energy = consumerList.stream().map(con -> con.getEnergySelfSupplied()).reduce(0.f, Float::sum) + consumerSelfSuppliedList.stream().map(con -> con.getEnergySelfSupplied()).reduce(0.f, Float::sum); energy += supplierList.stream().map(sup -> sup.getEnergyProducing()).reduce(0.f, Float::sum); return energy; } public float getAverageProductionInNetworkForHolonObject() { return getTotalProduction() / (float) getAmountOfHolonObjects(); } /** * returns the Varianz in Poduction * @return */ public float getVarianzInProductionInNetworkForHolonObjects() { float average = getAverageProductionInNetworkForHolonObject(); float sum = consumerList.stream().map(con -> squared(con.getEnergySelfSupplied() - average)).reduce(0.f, Float::sum) + consumerSelfSuppliedList.stream().map(con -> squared(con.getEnergySelfSupplied() - average)).reduce(0.f, Float::sum) + supplierList.stream().map(sup -> squared(sup.getEnergyProducing() - average)).reduce(0.f, Float::sum); return sum / (float) getAmountOfHolonObjects(); } public float getDeviationInProductionInNetworkForHolonObjects() { return (float)Math.sqrt(getVarianzInProductionInNetworkForHolonObjects()); } public float getVarianzInConsumptionInNetworkForHolonObjects() { float average = getAverageConsumptionInNetworkForHolonObject(); float sum = consumerList.stream().map(con -> squared(con.getEnergyFromConsumingElemnets() - average)).reduce(0.f, Float::sum) + consumerSelfSuppliedList.stream().map(con -> squared(con.getEnergyFromConsumingElemnets() - average)).reduce(0.f, Float::sum) + supplierList.stream().map(sup -> squared(sup.getEnergySelfConsuming() - average)).reduce(0.f, Float::sum); return sum / (float) getAmountOfHolonObjects(); } public float getDeviationInConsumptionInNetworkForHolonObjects() { return (float)Math.sqrt(getVarianzInConsumptionInNetworkForHolonObjects()); } //HelperFunction /** * * @return a list of energy */ public List getListOfEnergyThatIsOfferedByFlexibilitiesInThisNetwork() { List eleList = consumerList.stream().flatMap(con-> con.getModel().getElements().stream()).collect(Collectors.toList()); eleList.addAll(consumerSelfSuppliedList.stream().flatMap(con-> con.getModel().getElements().stream()).collect(Collectors.toList())); eleList.addAll(supplierList.stream().flatMap(con-> con.getModel().getElements().stream()).collect(Collectors.toList())); eleList.addAll(passivNoEnergyList.stream().flatMap(con-> con.getModel().getElements().stream()).collect(Collectors.toList())); return eleList.stream().filter(ele -> (ele.flexList.stream().anyMatch(flex -> flex.offered && flex.fulfillsConstrains())) ).map(ele -> -ele.getEnergyAtTimeStep(timestep) ).collect(Collectors.toList()) ; } public List getListOfEnergyInProductionThatIsOfferedByFlexibilitiesInThisNetwork(){ return getListOfEnergyThatIsOfferedByFlexibilitiesInThisNetwork().stream().filter(value -> (value > 0.f)).collect(Collectors.toList()); } public List getListOfEnergyInConsumptionThatIsOfferedByFlexibilitiesInThisNetwork(){ return getListOfEnergyThatIsOfferedByFlexibilitiesInThisNetwork().stream().filter(value -> (value < 0.f)).map(value -> -value).collect(Collectors.toList()); } public float getFlexibilityProductionCapacity() { return getListOfEnergyInProductionThatIsOfferedByFlexibilitiesInThisNetwork().stream().reduce(0.f, Float::sum); } public float getFlexibilityConsumptionCapacity() { return getListOfEnergyInConsumptionThatIsOfferedByFlexibilitiesInThisNetwork().stream().reduce(0.f, Float::sum); } public int getAmountOfProductionFlexibilities() { return getListOfEnergyInProductionThatIsOfferedByFlexibilitiesInThisNetwork().size(); } public int getAmountOfConsumptionFlexibilities() { return getListOfEnergyInConsumptionThatIsOfferedByFlexibilitiesInThisNetwork().size(); } public float getAverageFlexibilityProduction() { int amount = getAmountOfProductionFlexibilities(); return (amount > 0)? getFlexibilityProductionCapacity() / (float)amount : 0.f; } public float getAverageFlexibilityConsumption() { int amount = getAmountOfConsumptionFlexibilities(); return (amount > 0)? getFlexibilityConsumptionCapacity() / (float)amount : 0.f; } public float getVarianzInFlexibilitieConsumption() { float average = getAverageFlexibilityConsumption(); float sum = getListOfEnergyInConsumptionThatIsOfferedByFlexibilitiesInThisNetwork().stream().map(energy -> squared(energy - average)).reduce(0.f, Float::sum); int amountOfFlexibilities = getAmountOfConsumptionFlexibilities(); return (amountOfFlexibilities > 0)? sum / (float) amountOfFlexibilities : 0.f; } public float getVarianzInFlexibilitieProduction() { float average = getAverageFlexibilityProduction(); float sum = getListOfEnergyInProductionThatIsOfferedByFlexibilitiesInThisNetwork().stream().map(energy -> squared(energy - average)).reduce(0.f, Float::sum); int amountOfFlexibilities = getAmountOfProductionFlexibilities(); return (amountOfFlexibilities > 0)? sum / (float) amountOfFlexibilities : 0.f; } public float getDiviationInFlexibilityConsumption() { return (float) Math.sqrt(getVarianzInFlexibilitieConsumption()); } public float getDiviationInFlexibilityProduction() { return (float) Math.sqrt(getVarianzInFlexibilitieProduction()); } //Help Function private float squared(float input) { return (float) Math.pow(input, 2); } }