TopologieAlgorithmFramework.java 32 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929
  1. package api;
  2. import java.awt.BorderLayout;
  3. import java.awt.Component;
  4. import java.awt.Dimension;
  5. import java.awt.FlowLayout;
  6. import java.awt.image.BufferedImage;
  7. import java.io.BufferedWriter;
  8. import java.io.File;
  9. import java.io.FileOutputStream;
  10. import java.io.IOException;
  11. import java.io.OutputStreamWriter;
  12. import java.math.RoundingMode;
  13. import java.text.NumberFormat;
  14. import java.util.ArrayList;
  15. import java.util.Collections;
  16. import java.util.LinkedList;
  17. import java.util.List;
  18. import java.util.Locale;
  19. import java.util.function.BiFunction;
  20. import java.util.function.Consumer;
  21. import java.util.function.Supplier;
  22. import java.util.stream.Collectors;
  23. import javax.swing.BorderFactory;
  24. import javax.swing.Box;
  25. import javax.swing.BoxLayout;
  26. import javax.swing.ImageIcon;
  27. import javax.swing.JButton;
  28. import javax.swing.JCheckBox;
  29. import javax.swing.JFileChooser;
  30. import javax.swing.JFormattedTextField;
  31. import javax.swing.JLabel;
  32. import javax.swing.JOptionPane;
  33. import javax.swing.JPanel;
  34. import javax.swing.JProgressBar;
  35. import javax.swing.JScrollPane;
  36. import javax.swing.JSplitPane;
  37. import javax.swing.text.NumberFormatter;
  38. import classes.AbstractCpsObject;
  39. import classes.CpsUpperNode;
  40. import classes.Flexibility;
  41. import classes.HolonElement;
  42. import classes.HolonObject;
  43. import classes.HolonSwitch;
  44. import classes.HolonElement.Priority;
  45. import ui.controller.Control;
  46. import ui.controller.FlexManager.FlexState;
  47. import ui.controller.FlexManager.FlexWrapper;
  48. import ui.model.DecoratedGroupNode;
  49. import ui.model.DecoratedState;
  50. import ui.model.Model;
  51. import ui.model.DecoratedHolonObject.HolonObjectState;
  52. import ui.model.DecoratedSwitch.SwitchState;
  53. import ui.model.DecoratedNetwork;
  54. import ui.view.Console;
  55. public abstract class TopologieAlgorithmFramework implements AddOn{
  56. //Algo
  57. protected int rounds = 1;
  58. //Panel
  59. private JPanel content = new JPanel();
  60. protected Console console = new Console();
  61. private JPanel borderPanel = new JPanel();
  62. //Settings groupNode
  63. private DecoratedGroupNode dGroupNode = null;
  64. //access
  65. private ArrayList<AccessWrapper> access;
  66. LinkedList<List<Integer>> resetChain = new LinkedList<List<Integer>>();
  67. boolean algoUseElements = false, algoUseSwitches = true, algoUseFlexes = true;
  68. //time
  69. private long startTime;
  70. private RunProgressBar runProgressbar = new RunProgressBar();
  71. //concurrency
  72. private Thread runThread = new Thread();
  73. protected boolean cancel = false;
  74. //holeg interaction
  75. protected Control control;
  76. //printing
  77. private Printer runPrinter = new Printer(plottFileName());
  78. protected List<Double> runList = new LinkedList<Double>();
  79. //Parameter
  80. @SuppressWarnings("rawtypes")
  81. LinkedList<ParameterStepping> parameterSteppingList= new LinkedList<ParameterStepping>();
  82. protected boolean useStepping = false;
  83. public TopologieAlgorithmFramework(){
  84. content.setLayout(new BorderLayout());
  85. JSplitPane splitPane = new JSplitPane(JSplitPane.VERTICAL_SPLIT,
  86. createOptionPanel() , console);
  87. splitPane.setResizeWeight(0.0);
  88. content.add(splitPane, BorderLayout.CENTER);
  89. content.setPreferredSize(new Dimension(1200,800));
  90. }
  91. private JPanel createOptionPanel() {
  92. JPanel optionPanel = new JPanel(new BorderLayout());
  93. JScrollPane scrollPane = new JScrollPane(createParameterPanel());
  94. scrollPane.setBorder(BorderFactory.createTitledBorder("Parameter"));
  95. optionPanel.add(scrollPane, BorderLayout.CENTER);
  96. optionPanel.add(createButtonPanel(), BorderLayout.PAGE_END);
  97. return optionPanel;
  98. }
  99. private JPanel createParameterPanel() {
  100. JPanel parameterPanel = new JPanel(null);
  101. parameterPanel.setPreferredSize(new Dimension(510,300));
  102. borderPanel.setLayout(new BoxLayout(borderPanel, BoxLayout.PAGE_AXIS));
  103. addIntParameter("Rounds", rounds, intInput -> rounds = intInput, () -> rounds, 1);
  104. JScrollPane scrollPane = new JScrollPane(borderPanel);
  105. scrollPane.setBounds(10, 0, 850, 292);
  106. scrollPane.setBorder(BorderFactory.createEmptyBorder());
  107. parameterPanel.add(scrollPane);
  108. JProgressBar progressBar = runProgressbar.getJProgressBar();
  109. progressBar.setBounds(900, 35, 185, 20);
  110. progressBar.setStringPainted(true);
  111. parameterPanel.add(progressBar);
  112. return parameterPanel;
  113. }
  114. private JPanel createButtonPanel() {
  115. JPanel buttonPanel = new JPanel(new FlowLayout(FlowLayout.RIGHT));
  116. JButton resetButton = new JButton("Reset");
  117. resetButton.setToolTipText("Resets the State to before the Algorithm has runed.");
  118. resetButton.addActionListener(actionEvent -> reset());
  119. buttonPanel.add(resetButton);
  120. JButton cancelButton = new JButton("Cancel Run");
  121. cancelButton.addActionListener(actionEvent -> cancel());
  122. buttonPanel.add(cancelButton);
  123. JButton fitnessButton = new JButton("Fitness");
  124. fitnessButton.setToolTipText("Fitness for the current state.");
  125. fitnessButton.addActionListener(actionEvent -> fitness());
  126. buttonPanel.add(fitnessButton);
  127. JButton runButton = new JButton("Run");
  128. runButton.addActionListener(actionEvent -> {
  129. Runnable task = () -> run();
  130. runThread = new Thread(task);
  131. runThread.start();
  132. });
  133. buttonPanel.add(runButton);
  134. return buttonPanel;
  135. }
  136. //ParameterImports
  137. //int
  138. protected void addIntParameter(String parameterName, int parameterValue, Consumer<Integer> setter, Supplier<Integer> getter) {
  139. this.addIntParameter(parameterName, parameterValue, setter, getter, Integer.MIN_VALUE, Integer.MAX_VALUE);
  140. }
  141. protected void addIntParameter(String parameterName, int parameterValue, Consumer<Integer> setter, Supplier<Integer> getter, int parameterMinValue) {
  142. this.addIntParameter(parameterName, parameterValue, setter, getter, parameterMinValue, Integer.MAX_VALUE);
  143. }
  144. protected void addIntParameter(String parameterName, int parameterValue, Consumer<Integer> setter, Supplier<Integer> getter, int parameterMinValue, int parameterMaxValue) {
  145. JPanel singleParameterPanel = new JPanel();
  146. singleParameterPanel.setLayout(new BoxLayout(singleParameterPanel, BoxLayout.LINE_AXIS));
  147. singleParameterPanel.setAlignmentX(0.0f);
  148. singleParameterPanel.add(new JLabel(parameterName + ": "));
  149. singleParameterPanel.add(Box.createHorizontalGlue());
  150. NumberFormat format = NumberFormat.getIntegerInstance();
  151. format.setGroupingUsed(false);
  152. format.setParseIntegerOnly(true);
  153. NumberFormatter integerFormatter = new NumberFormatter(format);
  154. integerFormatter.setMinimum(parameterMinValue);
  155. integerFormatter.setMaximum(parameterMaxValue);
  156. integerFormatter.setCommitsOnValidEdit(true);
  157. JFormattedTextField singleParameterTextField = new JFormattedTextField(integerFormatter);
  158. singleParameterTextField.setValue(parameterValue);
  159. String minValue = (parameterMinValue == Integer.MIN_VALUE)?"Integer.MIN_VALUE":String.valueOf(parameterMinValue);
  160. String maxValue = (parameterMaxValue == Integer.MAX_VALUE)?"Integer.MAX_VALUE":String.valueOf(parameterMaxValue);
  161. singleParameterTextField.setToolTipText("Only integer \u2208 [" + minValue + "," + maxValue + "]");
  162. singleParameterTextField.addPropertyChangeListener(actionEvent -> setter.accept(Integer.parseInt(singleParameterTextField.getValue().toString())));
  163. singleParameterTextField.setMaximumSize(new Dimension(200, 30));
  164. singleParameterTextField.setPreferredSize(new Dimension(200, 30));
  165. singleParameterPanel.add(singleParameterTextField);
  166. ParameterStepping<Integer> intParameterStepping = new ParameterStepping<Integer>(setter, getter, Integer::sum , (a,b) -> a * b, 1, 1);
  167. intParameterStepping.useThisParameter = false;
  168. parameterSteppingList.add(intParameterStepping);
  169. JCheckBox useSteppingCheckBox = new JCheckBox();
  170. useSteppingCheckBox.setSelected(false);
  171. singleParameterPanel.add(useSteppingCheckBox);
  172. JLabel stepsLabel = new JLabel("Steps: ");
  173. stepsLabel.setEnabled(false);
  174. singleParameterPanel.add(stepsLabel);
  175. NumberFormatter stepFormatter = new NumberFormatter(format);
  176. stepFormatter.setMinimum(1);
  177. stepFormatter.setMaximum(Integer.MAX_VALUE);
  178. stepFormatter.setCommitsOnValidEdit(true);
  179. JFormattedTextField stepsTextField = new JFormattedTextField(stepFormatter);
  180. stepsTextField.setEnabled(false);
  181. stepsTextField.setValue(1);
  182. stepsTextField.setToolTipText("Only integer \u2208 [" + 1 + "," + Integer.MAX_VALUE + "]");
  183. stepsTextField.addPropertyChangeListener(actionEvent -> intParameterStepping.stepps = Integer.parseInt(stepsTextField.getValue().toString()));
  184. stepsTextField.setMaximumSize(new Dimension(40, 30));
  185. stepsTextField.setPreferredSize(new Dimension(40, 30));
  186. singleParameterPanel.add(stepsTextField);
  187. JLabel stepsSizeLabel = new JLabel("StepsSize: ");
  188. stepsSizeLabel.setEnabled(false);
  189. singleParameterPanel.add(stepsSizeLabel);
  190. JFormattedTextField stepsSizeTextField = new JFormattedTextField(stepFormatter);
  191. stepsSizeTextField.setEnabled(false);
  192. stepsSizeTextField.setValue(1);
  193. stepsSizeTextField.setToolTipText("Only integer \u2208 [" + 1 + "," + Integer.MAX_VALUE + "]");
  194. stepsSizeTextField.addPropertyChangeListener(actionEvent -> intParameterStepping.stepSize = Integer.parseInt(stepsSizeTextField.getValue().toString()));
  195. stepsSizeTextField.setMaximumSize(new Dimension(40, 30));
  196. stepsSizeTextField.setPreferredSize(new Dimension(40, 30));
  197. singleParameterPanel.add(stepsSizeTextField);
  198. useSteppingCheckBox.addActionListener(actionEvent -> {
  199. boolean enabled = useSteppingCheckBox.isSelected();
  200. intParameterStepping.useThisParameter = enabled;
  201. this.useStepping = this.parameterSteppingList.stream().anyMatch(parameter -> parameter.useThisParameter);
  202. stepsLabel.setEnabled(enabled);
  203. stepsTextField.setEnabled(enabled);
  204. stepsSizeLabel.setEnabled(enabled);
  205. stepsSizeTextField.setEnabled(enabled);
  206. });
  207. borderPanel.add(singleParameterPanel);
  208. }
  209. //double
  210. protected void addDoubleParameter(String parameterName, double parameterValue, Consumer<Double> setter, Supplier<Double> getter) {
  211. this.addDoubleParameter(parameterName, parameterValue, setter, getter, Double.MIN_VALUE, Double.MAX_VALUE);
  212. }
  213. protected void addDoubleParameter(String parameterName, double parameterValue, Consumer<Double> setter, Supplier<Double> getter, double parameterMinValue) {
  214. this.addDoubleParameter(parameterName, parameterValue, setter, getter, parameterMinValue, Double.MAX_VALUE);
  215. }
  216. protected void addDoubleParameter(String parameterName, double parameterValue, Consumer<Double> setter, Supplier<Double> getter, double parameterMinValue, double parameterMaxValue) {
  217. JPanel singleParameterPanel = new JPanel();
  218. singleParameterPanel.setLayout(new BoxLayout(singleParameterPanel, BoxLayout.LINE_AXIS));
  219. singleParameterPanel.setAlignmentX(0.0f);
  220. singleParameterPanel.add(new JLabel(parameterName + ": "));
  221. singleParameterPanel.add(Box.createHorizontalGlue());
  222. NumberFormat doubleFormat = NumberFormat.getNumberInstance(Locale.US);
  223. doubleFormat.setMinimumFractionDigits(1);
  224. doubleFormat.setMaximumFractionDigits(10);
  225. doubleFormat.setRoundingMode(RoundingMode.HALF_UP);
  226. NumberFormatter doubleFormatter = new NumberFormatter(doubleFormat);
  227. doubleFormatter.setMinimum(parameterMinValue);
  228. doubleFormatter.setMaximum(parameterMaxValue);
  229. doubleFormatter.setCommitsOnValidEdit(true);
  230. JFormattedTextField singleParameterTextField = new JFormattedTextField(doubleFormatter);
  231. singleParameterTextField.setValue(parameterValue);
  232. String minValue = (parameterMinValue == Double.MIN_VALUE)?"Double.MIN_VALUE":String.valueOf(parameterMinValue);
  233. String maxValue = (parameterMaxValue == Double.MAX_VALUE)?"Double.MAX_VALUE":String.valueOf(parameterMaxValue);
  234. singleParameterTextField.setToolTipText("Only double \u2208 [" + minValue + "," + maxValue + "]");
  235. singleParameterTextField.addPropertyChangeListener(actionEvent -> setter.accept(Double.parseDouble(singleParameterTextField.getValue().toString())));
  236. singleParameterTextField.setMaximumSize(new Dimension(200, 30));
  237. singleParameterTextField.setPreferredSize(new Dimension(200, 30));
  238. singleParameterPanel.add(singleParameterTextField);
  239. ParameterStepping<Double> doubleParameterStepping = new ParameterStepping<Double>(setter, getter, (a,b) -> a+b , (a,b) -> a * b, 1.0, 1);
  240. doubleParameterStepping.useThisParameter = false;
  241. parameterSteppingList.add(doubleParameterStepping);
  242. JCheckBox useSteppingCheckBox = new JCheckBox();
  243. useSteppingCheckBox.setSelected(false);
  244. singleParameterPanel.add(useSteppingCheckBox);
  245. JLabel stepsLabel = new JLabel("Steps: ");
  246. stepsLabel.setEnabled(false);
  247. singleParameterPanel.add(stepsLabel);
  248. NumberFormat format = NumberFormat.getIntegerInstance();
  249. format.setGroupingUsed(false);
  250. format.setParseIntegerOnly(true);
  251. NumberFormatter integerFormatter = new NumberFormatter(format);
  252. integerFormatter.setMinimum(1);
  253. integerFormatter.setMaximum(Integer.MAX_VALUE);
  254. integerFormatter.setCommitsOnValidEdit(true);
  255. JFormattedTextField stepsTextField = new JFormattedTextField(integerFormatter);
  256. stepsTextField.setEnabled(false);
  257. stepsTextField.setValue(1);
  258. stepsTextField.setToolTipText("Only integer \u2208 [" + 1 + "," + Integer.MAX_VALUE + "]");
  259. stepsTextField.addPropertyChangeListener(actionEvent -> doubleParameterStepping.stepps = Integer.parseInt(stepsTextField.getValue().toString()));
  260. stepsTextField.setMaximumSize(new Dimension(40, 30));
  261. stepsTextField.setPreferredSize(new Dimension(40, 30));
  262. singleParameterPanel.add(stepsTextField);
  263. JLabel stepsSizeLabel = new JLabel("StepsSize: ");
  264. stepsSizeLabel.setEnabled(false);
  265. singleParameterPanel.add(stepsSizeLabel);
  266. NumberFormatter doubleFormatterForStepping = new NumberFormatter(doubleFormat);
  267. doubleFormatterForStepping.setCommitsOnValidEdit(true);
  268. JFormattedTextField stepsSizeTextField = new JFormattedTextField(doubleFormatterForStepping);
  269. stepsSizeTextField.setEnabled(false);
  270. stepsSizeTextField.setValue(1.0);
  271. stepsSizeTextField.setToolTipText("Only double");
  272. stepsSizeTextField.addPropertyChangeListener(actionEvent -> doubleParameterStepping.stepSize = Double.parseDouble(stepsSizeTextField.getValue().toString()));
  273. stepsSizeTextField.setMaximumSize(new Dimension(40, 30));
  274. stepsSizeTextField.setPreferredSize(new Dimension(40, 30));
  275. singleParameterPanel.add(stepsSizeTextField);
  276. useSteppingCheckBox.addActionListener(actionEvent -> {
  277. boolean enabled = useSteppingCheckBox.isSelected();
  278. doubleParameterStepping.useThisParameter = enabled;
  279. this.useStepping = this.parameterSteppingList.stream().anyMatch(parameter -> parameter.useThisParameter);
  280. stepsLabel.setEnabled(enabled);
  281. stepsTextField.setEnabled(enabled);
  282. stepsSizeLabel.setEnabled(enabled);
  283. stepsSizeTextField.setEnabled(enabled);
  284. });
  285. borderPanel.add(singleParameterPanel);
  286. }
  287. //boolean
  288. protected void addBooleanParameter(String parameterName, boolean parameterValue, Consumer<Boolean> setter){
  289. JPanel singleParameterPanel = new JPanel();
  290. singleParameterPanel.setLayout(new BoxLayout(singleParameterPanel, BoxLayout.LINE_AXIS));
  291. singleParameterPanel.setAlignmentX(0.0f);
  292. singleParameterPanel.add(new JLabel(parameterName + ": "));
  293. singleParameterPanel.add(Box.createHorizontalGlue());
  294. JCheckBox useGroupNodeCheckBox = new JCheckBox();
  295. useGroupNodeCheckBox.setSelected(parameterValue);
  296. useGroupNodeCheckBox.addActionListener(actionEvent -> setter.accept(useGroupNodeCheckBox.isSelected()));
  297. singleParameterPanel.add(useGroupNodeCheckBox);
  298. borderPanel.add(singleParameterPanel);
  299. }
  300. private void startTimer(){
  301. startTime = System.currentTimeMillis();
  302. }
  303. private long printElapsedTime(){
  304. long elapsedMilliSeconds = System.currentTimeMillis() - startTime;
  305. console.println("Execution Time of Algo in Milliseconds:" + elapsedMilliSeconds);
  306. return elapsedMilliSeconds;
  307. }
  308. private void cancel() {
  309. if(runThread.isAlive()) {
  310. console.println("Cancel run.");
  311. cancel = true;
  312. runProgressbar.cancel();
  313. } else {
  314. console.println("Nothing to cancel.");
  315. }
  316. }
  317. private void fitness() {
  318. if(runThread.isAlive()) {
  319. console.println("Run have to be cancelled First.");
  320. return;
  321. }
  322. double currentFitness = evaluatePosition(extractPositionAndAccess());
  323. resetChain.removeLast();
  324. console.println("Actual Fitnessvalue: " + currentFitness);
  325. }
  326. protected double evaluatePosition(List<Integer> positionToEvaluate) {
  327. runProgressbar.step();
  328. // long startTime = System.currentTimeMillis(), endTime;
  329. control.getSimManager().resetFlexManagerForTimeStep(control.getModel().getCurIteration()); // execution time critical
  330. // endTime = System.currentTimeMillis();
  331. // console.print(" a:" + (endTime - startTime));
  332. // startTime = endTime;
  333. setState(positionToEvaluate); // execution time critical
  334. control.calculateStateOnlyForCurrentTimeStep();
  335. DecoratedState actualstate = control.getSimManager().getActualDecorState();
  336. double result = evaluateState(actualstate);
  337. return result;
  338. }
  339. protected abstract double evaluateState(DecoratedState actualstate);
  340. private void run() {
  341. cancel = false;
  342. control.guiDisable(true);
  343. runPrinter.openStream();
  344. runPrinter.println("");
  345. runPrinter.println("Start:" + stringStatFromActualState());
  346. runPrinter.closeStream();
  347. if(this.useStepping) {
  348. initParameterStepping();
  349. do {
  350. executeAlgoWithParameter();
  351. if(cancel) break;
  352. resetState();
  353. }while(updateOneParameter());
  354. resetParameterStepping();
  355. }else {
  356. executeAlgoWithParameter();
  357. }
  358. updateVisual();
  359. runProgressbar.finishedCancel();
  360. control.guiDisable(false);
  361. }
  362. @SuppressWarnings("rawtypes")
  363. private void initParameterStepping() {
  364. for(ParameterStepping param :this.parameterSteppingList) {
  365. param.init();
  366. }
  367. }
  368. @SuppressWarnings("rawtypes")
  369. private void resetParameterStepping() {
  370. for(ParameterStepping param :this.parameterSteppingList) {
  371. param.reset();
  372. }
  373. }
  374. @SuppressWarnings("rawtypes")
  375. private boolean updateOneParameter() {
  376. List<ParameterStepping> parameterInUseList = this.parameterSteppingList.stream().filter(param -> param.useThisParameter).collect(Collectors.toList());
  377. Collections.reverse(parameterInUseList);
  378. int lastParameter = parameterInUseList.size() - 1 ;
  379. int actualParameter = 0;
  380. for(ParameterStepping param : parameterInUseList) {
  381. if(param.canUpdate()) {
  382. param.update();
  383. return true;
  384. }else {
  385. if(actualParameter == lastParameter) break;
  386. param.reset();
  387. }
  388. actualParameter++;
  389. }
  390. //No Param can be updated
  391. return false;
  392. }
  393. private void executeAlgoWithParameter(){
  394. double startFitness = evaluatePosition(extractPositionAndAccess());
  395. console.println("BitLength: " + access.size());
  396. resetChain.removeLast();
  397. runPrinter.openStream();
  398. runPrinter.println("");
  399. runPrinter.println(algoInformationToPrint());
  400. console.println(algoInformationToPrint());
  401. runPrinter.closeStream();
  402. runProgressbar.start();
  403. Individual runBest = new Individual();
  404. runBest.fitness = Double.MAX_VALUE;
  405. for(int r = 0; r < rounds; r++)
  406. {
  407. startTimer();
  408. Individual roundBest = executeAlgo();
  409. if(cancel)return;
  410. long executionTime = printElapsedTime();
  411. runPrinter.openStream();
  412. runPrinter.println(runList.stream().map(Object::toString).collect(Collectors.joining(", ")));
  413. runPrinter.println(stringStatFromActualState());
  414. runPrinter.println("Result: " + roundBest.fitness + " ExecutionTime:" + executionTime);
  415. runPrinter.closeStream();
  416. resetState();
  417. if(roundBest.fitness < runBest.fitness) runBest = roundBest;
  418. }
  419. control.getSimManager().resetFlexManagerForTimeStep(control.getModel().getCurIteration());
  420. this.extractPositionAndAccess();
  421. setState(runBest.position);
  422. updateVisual();
  423. console.println("Start: " + startFitness);
  424. console.println("AlgoResult: " + runBest.fitness);
  425. }
  426. protected abstract Individual executeAlgo();
  427. private void reset() {
  428. if(runThread.isAlive()) {
  429. console.println("Run have to be cancelled First.");
  430. return;
  431. }
  432. if(!resetChain.isEmpty()) {
  433. console.println("Resetting..");
  434. setState(resetChain.getFirst());
  435. control.getSimManager().resetFlexManagerForTimeStep(control.getModel().getCurIteration());
  436. resetChain.clear();
  437. control.resetSimulation();
  438. control.setCurIteration(0);
  439. updateVisual();
  440. }else {
  441. console.println("No run inistialized.");
  442. }
  443. }
  444. /**
  445. * To let the User See the current state without touching the Canvas.
  446. */
  447. private void updateVisual() {
  448. control.calculateStateAndVisualForCurrentTimeStep();
  449. }
  450. /**
  451. * Sets the Model back to its original State before the LAST run.
  452. */
  453. private void resetState() {
  454. control.getSimManager().resetFlexManagerForTimeStep(control.getModel().getCurIteration());
  455. setState(resetChain.getLast());
  456. }
  457. /**
  458. * Sets the State out of the given position for calculation or to show the user.
  459. * @param position
  460. */
  461. private void setState(List<Integer> position) {
  462. int i = 0;
  463. for(Integer integer: position) {
  464. access.get(i++).setState(integer);
  465. }
  466. }
  467. /**
  468. * Method to get the current Position alias a ListOf Booleans for aktive settings on the Objects on the Canvas.
  469. * Also initialize the Access Hashmap to swap faster positions.
  470. * @param model
  471. * @return
  472. */
  473. protected List<Integer> extractPositionAndAccess() {
  474. Model model = control.getModel();
  475. access= new ArrayList<AccessWrapper>();
  476. List<Integer> initialState = new ArrayList<Integer>();
  477. rollOutNodes((dGroupNode != null)? dGroupNode.getModel().getNodes() :model.getObjectsOnCanvas(), initialState, model.getCurIteration());
  478. resetChain.add(initialState);
  479. //console.println(access.stream().map(Object::toString).collect(Collectors.joining(", ")));
  480. return initialState;
  481. }
  482. /**
  483. * Method to extract the Informations recursively out of the Model.
  484. * @param nodes
  485. * @param positionToInit
  486. * @param timeStep
  487. */
  488. private void rollOutNodes(List<AbstractCpsObject> nodes, List<Integer> positionToInit, int timeStep) {
  489. for(AbstractCpsObject aCps : nodes) {
  490. if(aCps instanceof CpsUpperNode) {
  491. rollOutNodes(((CpsUpperNode)aCps).getNodes(), positionToInit ,timeStep );
  492. }
  493. }
  494. }
  495. private String stringStatFromActualState() {
  496. if(dGroupNode != null)
  497. {
  498. //GetActualDecoratedGroupNode
  499. dGroupNode = control.getSimManager().getActualVisualRepresentationalState().getCreatedGroupNodes().get(dGroupNode.getModel());
  500. int amountOfSupplier = dGroupNode.getAmountOfSupplier();
  501. int amountOfConsumer = dGroupNode.getAmountOfConsumer();
  502. int amountOfPassiv = dGroupNode.getAmountOfPassiv();
  503. int amountOfObjects = amountOfSupplier + amountOfConsumer + amountOfPassiv;
  504. int unSuppliedConsumer = dGroupNode.getAmountOfConsumerWithState(HolonObjectState.NOT_SUPPLIED);
  505. int partiallySuppliedConsumer = dGroupNode.getAmountOfConsumerWithState(HolonObjectState.PARTIALLY_SUPPLIED);
  506. int suppliedConsumer = dGroupNode.getAmountOfConsumerWithState(HolonObjectState.SUPPLIED);
  507. int overSuppliedConsumer = dGroupNode.getAmountOfConsumerWithState(HolonObjectState.OVER_SUPPLIED);
  508. int activeElements = dGroupNode.getAmountOfAktiveElemntsFromHolonObjects();
  509. int elements = dGroupNode.getAmountOfElemntsFromHolonObjects();
  510. return "HolonObjects["
  511. + " Producer: " + amountOfSupplier + "/" + amountOfObjects + "("+ (float)amountOfSupplier/(float)amountOfObjects * 100 + "%)"
  512. + " Unsupplied: " + unSuppliedConsumer + "/" + amountOfObjects + "("+ (float)unSuppliedConsumer/(float)amountOfObjects * 100 + "%)"
  513. + " PartiallySupplied: " + partiallySuppliedConsumer + "/" + amountOfObjects + "("+ (float)partiallySuppliedConsumer/(float)amountOfObjects * 100 + "%)"
  514. + " Supplied: " + suppliedConsumer + "/" + amountOfObjects + "("+ (float)suppliedConsumer/(float)amountOfObjects * 100 + "%)"
  515. + " Passiv: " + overSuppliedConsumer + "/" + amountOfObjects + "("+ (float)overSuppliedConsumer/(float)amountOfObjects * 100 + "%)"
  516. + "]" + " HolonElemnts["
  517. + " Active: " + activeElements + "/" + elements + "("+ (float)activeElements/(float)elements * 100 + "%)"
  518. + "]";
  519. }
  520. DecoratedState state = control.getSimManager().getActualDecorState();
  521. int amountOfSupplier = 0, amountOfConsumer = 0, amountOfPassiv = 0, unSuppliedConsumer = 0, partiallySuppliedConsumer = 0, suppliedConsumer = 0, overSuppliedConsumer = 0;
  522. int activeElements = 0, amountOfelements = 0;
  523. int totalConsumption = 0, totalProduction = 0;
  524. for(DecoratedNetwork net : state.getNetworkList()) {
  525. amountOfConsumer += net.getAmountOfConsumer();
  526. amountOfSupplier += net.getAmountOfSupplier();
  527. amountOfPassiv += net.getAmountOfPassiv();
  528. unSuppliedConsumer += net.getAmountOfConsumerWithState(HolonObjectState.NOT_SUPPLIED);
  529. partiallySuppliedConsumer += net.getAmountOfConsumerWithState(HolonObjectState.PARTIALLY_SUPPLIED);
  530. suppliedConsumer += net.getAmountOfConsumerWithState(HolonObjectState.SUPPLIED);
  531. overSuppliedConsumer += net.getAmountOfConsumerWithState(HolonObjectState.OVER_SUPPLIED);
  532. amountOfelements += net.getAmountOfElements();
  533. activeElements += net.getAmountOfActiveElements();
  534. totalConsumption += net.getTotalConsumption();
  535. totalProduction += net.getTotalProduction();
  536. }
  537. int amountOfObjects = amountOfSupplier + amountOfConsumer + amountOfPassiv;
  538. int difference = Math.abs(totalProduction - totalConsumption);
  539. List<Flexibility> flexActiveList = control.getSimManager().getActualFlexManager().getAllFlexWrapperWithState(FlexState.IN_USE).stream().map(flex -> flex.getFlex()).collect(Collectors.toList());
  540. int amountActiveEssential = (int)flexActiveList.stream().filter(flex -> flex.getElement().getPriority() == Priority.Essential).count();
  541. int amountActiveHigh = (int)flexActiveList.stream().filter(flex -> flex.getElement().getPriority() == Priority.High).count();
  542. int amountActiveMedium = (int)flexActiveList.stream().filter(flex -> flex.getElement().getPriority() == Priority.Medium).count();
  543. int amountActiveLow = (int)flexActiveList.stream().filter(flex -> flex.getElement().getPriority() == Priority.Low).count();
  544. int amountActiveFlexibilities = amountActiveEssential + amountActiveHigh + amountActiveMedium + amountActiveLow;
  545. int amountHolons = state.getNetworkList().size();
  546. int amountSwitch = state.getDecoratedSwitches().size();
  547. int amountActiveSwitch = (int)state.getDecoratedSwitches().stream().filter(dswitch -> (dswitch.getState() == SwitchState.Closed)).count();
  548. return "HolonObjects["
  549. + " Passiv: " + percentage(amountOfPassiv, amountOfObjects)
  550. + " Producer: " + percentage(amountOfSupplier, amountOfObjects)
  551. + " Consumer: " + percentage(amountOfConsumer, amountOfObjects)
  552. + " Unsupplied: " + percentage(unSuppliedConsumer, amountOfConsumer)
  553. + " PartiallySupplied: " + percentage(partiallySuppliedConsumer, amountOfObjects)
  554. + " Supplied: " + percentage(suppliedConsumer, amountOfConsumer)
  555. + " Over: " + percentage(overSuppliedConsumer, amountOfConsumer)
  556. + "]" + " HolonElemnts["
  557. + " Active: " + percentage(activeElements, amountOfelements)
  558. + "]" + "Flexibilities_active["
  559. + " Essential: " + percentage(amountActiveEssential, amountActiveFlexibilities)
  560. + " High: " + percentage(amountActiveHigh, amountActiveFlexibilities)
  561. + " Medium: " + percentage(amountActiveMedium, amountActiveFlexibilities)
  562. + " Low: " + percentage(amountActiveLow, amountActiveFlexibilities)
  563. + "]" + " activeSwitches:" + percentage(amountActiveSwitch,amountSwitch)
  564. + " Holons: " + amountHolons
  565. + " totalConsumption: " + totalConsumption
  566. + " totalProduction: " + totalProduction
  567. + " difference: " + difference;
  568. }
  569. private String percentage(int actual, int max) {
  570. return actual + "/" + max + "("+ (float)actual/(float)max * 100 + "%)";
  571. }
  572. @Override
  573. public JPanel getPanel() {
  574. return content;
  575. }
  576. @Override
  577. public void setController(Control control) {
  578. this.control = control;
  579. }
  580. private class RunProgressBar{
  581. //progressbar
  582. private JProgressBar progressBar = new JProgressBar();
  583. private int count = 0;
  584. private boolean isActive = false;
  585. public void step() {
  586. if(isActive) progressBar.setValue(count++);
  587. }
  588. public void start() {
  589. progressBar.setIndeterminate(false);
  590. count = 0;
  591. isActive = true;
  592. progressBar.setValue(0);
  593. progressBar.setMaximum(getProgressBarMaxCount());
  594. }
  595. public void cancel() {
  596. isActive = false;
  597. progressBar.setIndeterminate(true);
  598. }
  599. public void finishedCancel() {
  600. progressBar.setIndeterminate(false);
  601. progressBar.setValue(0);
  602. }
  603. public JProgressBar getJProgressBar(){
  604. return progressBar;
  605. }
  606. }
  607. protected abstract int getProgressBarMaxCount();
  608. protected abstract String algoInformationToPrint();
  609. protected abstract String plottFileName();
  610. public class Printer{
  611. private JFileChooser fileChooser = new JFileChooser();
  612. private BufferedWriter out;
  613. public Printer(String filename){
  614. fileChooser.setCurrentDirectory(new File(System.getProperty("user.dir")));
  615. fileChooser.setSelectedFile(new File(filename));
  616. }
  617. public void openStream() {
  618. File file = fileChooser.getSelectedFile();
  619. try {
  620. file.createNewFile();
  621. out = new BufferedWriter(new OutputStreamWriter(
  622. new FileOutputStream(file, true), "UTF-8"));
  623. } catch (IOException e) {
  624. System.out.println(e.getMessage());
  625. }
  626. }
  627. public void println(String stringToPrint) {
  628. try {
  629. out.write(stringToPrint);
  630. out.newLine();
  631. } catch (IOException e) {
  632. System.out.println(e.getMessage());
  633. }
  634. }
  635. public void closeStream() {
  636. try {
  637. out.close();
  638. } catch (IOException e) {
  639. System.out.println(e.getMessage());
  640. }
  641. }
  642. }
  643. /**
  644. * A Wrapper Class for Access HolonElement and HolonSwitch in one Element and not have to split the List.
  645. */
  646. private class AccessWrapper {
  647. public AccessWrapper(int a) {
  648. }
  649. public void setState(int state) {
  650. //TODO set state
  651. }
  652. public String toString() {
  653. return "Hollow";
  654. }
  655. }
  656. /**
  657. * To create Random and maybe switch the random generation in the future.
  658. */
  659. protected static class Random{
  660. private static java.util.Random random = new java.util.Random();
  661. /**
  662. * True or false
  663. * @return the random boolean.
  664. */
  665. public static boolean nextBoolean(){
  666. return random.nextBoolean();
  667. }
  668. /**
  669. * Between 0.0(inclusive) and 1.0 (exclusive)
  670. * @return the random double.
  671. */
  672. public static double nextDouble() {
  673. return random.nextDouble();
  674. }
  675. /**
  676. * Random Int in Range [min;max[ with UniformDistirbution
  677. * @param min
  678. * @param max
  679. * @return
  680. */
  681. public static int nextIntegerInRange(int min, int max) {
  682. int result = min;
  683. try {
  684. result = min + random.nextInt(max - min);
  685. }catch(java.lang.IllegalArgumentException e){
  686. System.err.println("min : " + min + " max : " + max);
  687. System.err.println("max should be more then min");
  688. }
  689. return result;
  690. }
  691. }
  692. private class Handle<T>{
  693. public T object;
  694. Handle(T object){
  695. this.object = object;
  696. }
  697. public String toString() {
  698. return object.toString();
  699. }
  700. }
  701. public class Individual {
  702. public double fitness;
  703. public List<Integer> position;
  704. public Individual(){};
  705. /**
  706. * Copy Constructor
  707. */
  708. public Individual(Individual c){
  709. position = c.position.stream().collect(Collectors.toList());
  710. fitness = c.fitness;
  711. }
  712. }
  713. protected class ParameterStepping<T>{
  714. boolean useThisParameter = false;
  715. String paramaterName;
  716. private int count = 0;
  717. int stepps;
  718. T stepSize;
  719. T startValue;
  720. Consumer<T> setter;
  721. Supplier<T> getter;
  722. BiFunction<Integer,T,T> multyply;
  723. BiFunction<T,T,T> add;
  724. ParameterStepping(Consumer<T> setter, Supplier<T> getter, BiFunction<T,T,T> add, BiFunction<Integer,T,T> multyply, T stepSize, int stepps){
  725. this.setter = setter;
  726. this.getter = getter;
  727. this.multyply = multyply;
  728. this.add = add;
  729. this.stepSize = stepSize;
  730. this.stepps = stepps;
  731. }
  732. void init() {
  733. startValue = getter.get();
  734. }
  735. boolean canUpdate() {
  736. return count < stepps;
  737. }
  738. void update(){
  739. if(canUpdate()) {
  740. setter.accept(add.apply(startValue, multyply.apply(count + 1, stepSize)));
  741. count ++;
  742. }
  743. }
  744. void reset() {
  745. setter.accept(startValue);
  746. count = 0;
  747. }
  748. }
  749. }