Holon.java 22 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768
  1. package classes;
  2. import java.util.ArrayList;
  3. import java.util.Collections;
  4. import java.util.HashMap;
  5. import java.util.List;
  6. import java.util.UUID;
  7. import classes.holonControlUnit.HolonControlUnit;
  8. import classes.holonControlUnit.OptimizationManager;
  9. import classes.holonControlUnit.StateEstimator.StateIndicator;
  10. import ui.controller.Control;
  11. import ui.model.DecoratedNetwork;
  12. import ui.model.IntermediateCableWithState;
  13. import ui.model.MinimumModel;
  14. import ui.model.Model;
  15. public class Holon {
  16. public String name = new String();
  17. private Holon parent = null;
  18. public ArrayList<Holon> childHolons = new ArrayList<Holon>();
  19. private List<HolonElement> elements = new ArrayList<HolonElement>();
  20. //HolonObject is the lowest representation of a holon.
  21. private final HolonObject holonObject;
  22. public final boolean isPhysical;
  23. public HolonControlUnit holonControlUnit;
  24. private String uniqueID;
  25. public Model model;
  26. private MinimumModel minModel;
  27. private int mergeCounter = 0, splitCounter = 0, indeCounter = 0, kickCounter = 0;
  28. private int[] stateCounter = {0, 0, 0};
  29. public Holon(String name, Model model) {
  30. this.name = name;
  31. this.holonObject = null;
  32. isPhysical = false;
  33. this.uniqueID = UUID.randomUUID().toString();
  34. this.model = model;
  35. this.holonControlUnit = new HolonControlUnit(this);
  36. this.minModel = new MinimumModel(new ArrayList<AbstractCanvasObject>(), new ArrayList<Edge>());
  37. }
  38. public Holon(HolonObject object, Model model) {
  39. holonObject = object;
  40. object.holon = this;
  41. name = object.getName();
  42. elements.addAll(object.getElements());
  43. for(HolonElement ele : elements) {
  44. ele.holon = this;
  45. }
  46. isPhysical = true;
  47. this.uniqueID = UUID.randomUUID().toString();
  48. this.model = model;
  49. this.holonControlUnit = new HolonControlUnit(this);
  50. ArrayList<AbstractCanvasObject> list = new ArrayList<AbstractCanvasObject>();
  51. list.add(object);
  52. this.minModel = new MinimumModel(list, new ArrayList<Edge>());
  53. }
  54. public void addElement(HolonElement element) {
  55. element.holon = this;
  56. elements.add(element);
  57. }
  58. public void removeElement(HolonElement element) {
  59. element.holon = null;
  60. elements.remove(element);
  61. }
  62. public int elementsCount() {
  63. return elements.size();
  64. }
  65. public void addChild(Holon child) {
  66. if(child.equals(this)) {
  67. System.err.println(this.uniqueID+" wants to merge itself");
  68. }
  69. if(!this.childHolons.contains(child)) {
  70. child.setParent(this);
  71. this.childHolons.add(child);
  72. }
  73. if(this.parent != null) {
  74. this.holonControlUnit.addSubHolon(child);
  75. }
  76. }
  77. public void addChildHolon(Holon child, int index) {
  78. if(!this.childHolons.contains(child)) {
  79. child.setParent(this);
  80. childHolons.add(index, child);
  81. }
  82. if(this.parent != null) {
  83. this.holonControlUnit.addSubHolon(child);
  84. }
  85. }
  86. public void removeChildHolon(Holon child) {
  87. child.setParent(null);
  88. childHolons.remove(child);
  89. if(this.parent == null)
  90. return;
  91. this.holonControlUnit.getHierarchyController().removeSubHolon(child.getUniqueID());
  92. this.holonControlUnit.getHierarchyController().getPathsToChildren().remove(child);
  93. revalidateMinModel(child);
  94. }
  95. public void removeFromParent() {
  96. if(parent != null) {
  97. parent.removeChildHolon(this);
  98. }
  99. this.setParent(null);
  100. }
  101. public int getChildCount() {
  102. return childHolons.size();
  103. }
  104. public Holon getParent() {
  105. return parent;
  106. }
  107. public void setParent(Holon parent) {
  108. // System.out.println("fick dich1");
  109. if(parent == this || isASubordinatedHolon(parent))
  110. return;
  111. this.parent = parent;
  112. this.holonControlUnit.getHierarchyController().setSuperHolon(parent != null ? parent.getUniqueID() : this.model.getStateHolon().getUniqueID());
  113. }
  114. public HolonObject getHolonObject() {
  115. return holonObject;
  116. }
  117. public List<Holon> getChildView(){
  118. return Collections.unmodifiableList(childHolons);
  119. }
  120. public List<HolonElement> getElementView(){
  121. return Collections.unmodifiableList(elements);
  122. }
  123. @Override
  124. public String toString() {
  125. return name;
  126. }
  127. public void reassignAllChildren(Holon other) {
  128. for(Holon child: this.childHolons) {
  129. other.merge(child);
  130. }
  131. childHolons.clear();
  132. }
  133. public void removeAllRefrences() {
  134. this.setParent(null);
  135. this.childHolons.clear();
  136. this.elements.clear();
  137. }
  138. public int getLayer() {
  139. if(this.parent == null)
  140. return 0;
  141. if(this.parent.equals(this)) {
  142. return 0;
  143. }
  144. return parent != null ? parent.getLayer() + 1 : 0;
  145. }
  146. public Holon cloneWithoutParent() {
  147. Holon cloned = new Holon(this.name, this.model);
  148. model.getHolonsByID().put(cloned.getUniqueID(), cloned);
  149. cloned.childHolons = this.childHolons;
  150. cloned.elements = this.elements;
  151. return cloned;
  152. }
  153. public boolean checkHolonArePhysicalConnected(Holon other, Control control) {
  154. HashMap<HolonObject, DecoratedNetwork> table = control.getSimManager().getActualDecorState().getHolonObjectNetworkTable();
  155. HolonObject a = tryGetAPhysicalHolon();
  156. HolonObject b = other.tryGetAPhysicalHolon();
  157. boolean aHolonIsPureAbstract = a == null || b == null;
  158. return aHolonIsPureAbstract || table.get(a) == table.get(b);
  159. }
  160. private HolonObject tryGetAPhysicalHolon() {
  161. if(holonObject != null) {
  162. return holonObject;
  163. }
  164. for(Holon holon : childHolons) {
  165. HolonObject object = holon.tryGetAPhysicalHolon();
  166. if(object != null) {
  167. return object;
  168. }
  169. }
  170. return null;
  171. }
  172. @Deprecated
  173. public void checkRepairHolarchy(HashMap<HolonObject, DecoratedNetwork> table, Holon stateHolon) {
  174. if(childHolons.isEmpty()) {
  175. return;
  176. }
  177. //To establish the invariant that all child holons are repaired
  178. for(Holon other : childHolons) {
  179. other.checkRepairHolarchy(table, stateHolon);
  180. }
  181. //Repair this Holon
  182. HolonObject first = tryGetAPhysicalHolon();
  183. if(first == null) {
  184. return;
  185. }
  186. List<Holon> removeList = new ArrayList<Holon>();
  187. for(Holon other : childHolons) {
  188. HolonObject otherHolonObject = other.tryGetAPhysicalHolon();
  189. boolean isPureAbstract = otherHolonObject == null;
  190. if(isPureAbstract) {
  191. continue;
  192. }
  193. boolean isPhysicalConnected = model.checkHolonObjectsAreConnected(this, other);
  194. if(!isPhysicalConnected) {
  195. removeList.add(other);
  196. }
  197. }
  198. //Remove holons
  199. for(Holon holon : removeList) {
  200. holon.split(null);
  201. }
  202. }
  203. public void addNewVirtualNeighbor(String virtualNeighbor) {
  204. if(!this.uniqueID.equals(virtualNeighbor)) {
  205. this.holonControlUnit.addNewVirtualNeighbor(virtualNeighbor);
  206. }
  207. }
  208. public String getUniqueID() {
  209. return uniqueID;
  210. }
  211. public ArrayList<HolonObject> getAllHolonObjects() {
  212. return this.getMinimumModel().getHolonObjectList();
  213. }
  214. public ArrayList<AbstractCanvasObject> getAllObjects(){
  215. ArrayList<AbstractCanvasObject> list = new ArrayList<AbstractCanvasObject>();
  216. list.addAll(this.minModel.getHolonObjectList());
  217. list.addAll(this.minModel.getNodeList());
  218. list.addAll(this.minModel.getSwitchList());
  219. list.addAll(this.minModel.getUppderNodeList());
  220. return list;
  221. }
  222. public MinimumModel getMinimumModel() {
  223. return this.minModel;
  224. }
  225. /**
  226. * merge this holon with the specified child holon
  227. * @param child
  228. */
  229. public void merge(Holon child) {
  230. if(!this.model.getHolonsByID().containsKey(child.getUniqueID())) {
  231. System.err.println("could not find: "+child.getHolonObject());
  232. return;
  233. }
  234. if(this.isASubordinatedHolon(child)) {
  235. System.err.println(this.uniqueID+"child is already a subordinated holon "+child.getUniqueID());
  236. return;
  237. }
  238. if(this.childHolons.contains(child)) {
  239. return;
  240. }
  241. if(this.parent == null) {
  242. //this is the state holon which does not need to compute any paths
  243. this.addChild(child);
  244. return;
  245. }
  246. HashMap<Float, ArrayList<Edge>> paths = this.model.getShortestPathToHolarchy(this.minModel, child.getMinimumModel());
  247. HashMap<Float, ArrayList<Edge>> free_paths = new HashMap<Float, ArrayList<Edge>>();
  248. HashMap<Float, ArrayList<Edge>> occ_paths = new HashMap<Float, ArrayList<Edge>>();
  249. HashMap<ArrayList<Edge>, List<Holon>> occ_by = new HashMap<>();
  250. for(Float f : paths.keySet()) {
  251. ArrayList<Edge> path = paths.get(f);
  252. List<Holon> holder = isPathOccupied(path);
  253. if(holder.size() == 0 || holder.contains(this) || holder.contains(this.parent)) {
  254. //path between this holon and child holon is free
  255. free_paths.put(f, path);
  256. } else {
  257. //path between this holon and child holon is already occupied
  258. occ_paths.put(f, path);
  259. occ_by.put(path, holder);
  260. }
  261. }
  262. if(free_paths.size() > 0) {
  263. //there is a free path, take it and add child directly to sub holons
  264. ArrayList<Edge> path = free_paths.get(getShortestPath(free_paths));
  265. Holon holder = this.containsPath(path, this);
  266. if(holder != null && !holder.equals(this)) {
  267. //the path already used by a child holon
  268. holder.merge(child);
  269. return;
  270. }
  271. this.addChild(child);
  272. this.addChildToMinModel(child, path);
  273. this.holonControlUnit.getHierarchyController().getPathsToChildren().put(child, path);
  274. return;
  275. }
  276. if(occ_paths.size() < 1) {
  277. System.err.println("something went wrong when looking for shortest path while merging "+this.uniqueID+" and "+child.getUniqueID());
  278. }
  279. ArrayList<ArrayList<Edge>> shortestPaths = sortPaths(occ_paths);
  280. //take the shortest path occupied by another holon
  281. for(ArrayList<Edge> path : shortestPaths) {
  282. List<Holon> holder = occ_by.get(path);
  283. if(holder.size() == 1) {
  284. this.split(holder.get(0));
  285. this.addChild(child);
  286. this.addChildToMinModel(child, path);
  287. this.holonControlUnit.getHierarchyController().getPathsToChildren().put(child, path);
  288. return;
  289. }
  290. }
  291. System.err.println("=>da haben wir den salat");
  292. if(child.parent == null)
  293. this.model.getStateHolon().addChild(child);
  294. }
  295. public void merge(Holon child, ArrayList<Edge> path, Holon occupier) {
  296. if(occupier == null) {
  297. if(child.getParent() != null) {
  298. child.getParent().removeChildHolon(child);
  299. }
  300. this.addChild(child);
  301. this.addChildToMinModel(child, path);
  302. this.holonControlUnit.getHierarchyController().getPathsToChildren().put(child, path);
  303. } else {
  304. if(this.isASubordinatedHolon(occupier) || child.isASubordinatedHolon(occupier)) {
  305. return;
  306. }
  307. if(child.getParent() != null) {
  308. child.getParent().removeChildHolon(child);
  309. }
  310. this.split(occupier);
  311. this.addChild(child);
  312. this.addChildToMinModel(child, path);
  313. this.holonControlUnit.getHierarchyController().getPathsToChildren().put(child, path);
  314. }
  315. this.incMergeCounter();
  316. }
  317. /**
  318. * checks whether a path is occupied
  319. * if true returns the holons in which the path is located
  320. * @param path
  321. * @return
  322. */
  323. public List<Holon> isPathOccupied(ArrayList<Edge> path) {
  324. Holon h = this.parent;
  325. Holon r = this;
  326. List<Holon> holder = new ArrayList<>();
  327. while(h != null) {
  328. Holon ho = h.containsPath(path, r);
  329. if(ho != null && ho.getParent() != null) {
  330. //found a holon which contains the path
  331. holder.add(ho);
  332. }
  333. r = h;
  334. h = h.parent;
  335. }
  336. return holder;
  337. }
  338. public List<Holon> getPathToChildOccupiedByParent() {
  339. List<Holon> list = new ArrayList<>();
  340. for(Holon child : this.holonControlUnit.getHierarchyController().getPathsToChildren().keySet()) {
  341. ArrayList<Edge> path = this.holonControlUnit.getHierarchyController().getPathsToChildren().get(child);
  342. List<Holon> holder = this.isPathOccupied(path);
  343. if(holder.contains(this.parent))
  344. list.add(child);
  345. }
  346. return list;
  347. }
  348. public ArrayList<ArrayList<Edge>> sortPaths(HashMap<Float, ArrayList<Edge>> paths) {
  349. ArrayList<ArrayList<Edge>> shortestPaths = new ArrayList<ArrayList<Edge>>();
  350. while(paths.size() > 0) {
  351. shortestPaths.add(paths.remove(getShortestPath(paths)));
  352. }
  353. return shortestPaths;
  354. }
  355. public Float getShortestPath(HashMap<Float, ArrayList<Edge>> paths){
  356. float min = Float.MAX_VALUE;
  357. for(Float f : paths.keySet()) {
  358. if(f < min) {
  359. min = f;
  360. }
  361. }
  362. return min;
  363. }
  364. /**
  365. * removes this holon from current superholon and merge with new superholon
  366. */
  367. public void split(Holon newParent) {
  368. //ensure that this holarchy can run independent(path is not occupied by superholon) from the superholon
  369. if(this.parent == null || !this.parent.canRunIndependent(this)) {
  370. return;
  371. }
  372. if(newParent == null) {
  373. newParent = this.model.getStateHolon();
  374. this.incSplitCounter();
  375. }
  376. this.parent.removeChildHolon(this);
  377. this.holonControlUnit.getHierarchyController().resetVirtualNeighbors();
  378. newParent.merge(this);
  379. }
  380. public void splitById(String id) {
  381. Holon child = this.model.getHolonsByID().get(id);
  382. if(child.parent == this)
  383. child.split(null);
  384. }
  385. /**
  386. * recalculates the min model after a holon was added to a subholon
  387. * does NOT recalculate the shortest paths between its subholons
  388. * only the minmodel of the specified child holon was modified
  389. */
  390. public void recalculateMinModel(Holon child) {
  391. ArrayList<AbstractCanvasObject> objects = this.getAllObjects();
  392. ArrayList<Edge> edges = new ArrayList<Edge>();
  393. for(IntermediateCableWithState icws : this.minModel.getEdgeList()) {
  394. edges.add(icws.getModel());
  395. }
  396. MinimumModel cmm = child.getMinimumModel();
  397. for(AbstractCanvasObject aco : child.getAllObjects()) {
  398. if(!objects.contains(aco)) {
  399. objects.add(aco);
  400. }
  401. }
  402. for(IntermediateCableWithState icws : cmm.getEdgeList()) {
  403. Edge e = icws.getModel();
  404. if(!edges.contains(e)) {
  405. edges.add(e);
  406. }
  407. }
  408. this.minModel = new MinimumModel(objects, edges);
  409. //notify superholon to recalculate its minModel
  410. if(this.parent != null && this.parent.getParent() != null && this.parent != this) {
  411. this.parent.recalculateMinModel(this);
  412. }
  413. }
  414. /**
  415. * adds a child and its min model (incl. all its subholons) to this min model
  416. * @param child
  417. */
  418. private void addChildToMinModel(Holon child, ArrayList<Edge> path) {
  419. if(this.minModel.getHolonObjectList().contains(child.getHolonObject()) || this.parent == null)
  420. return;
  421. ArrayList<Edge> edgeList = new ArrayList<Edge>();
  422. // add all holon objects that are part of this holarchy
  423. edgeList.addAll(path);
  424. for(IntermediateCableWithState icws : this.minModel.getEdgeList()) {
  425. if(!edgeList.contains(icws.getModel())) {
  426. edgeList.add(icws.getModel());
  427. }
  428. }
  429. for(IntermediateCableWithState icws : child.minModel.getEdgeList()) {
  430. if(!edgeList.contains(icws.getModel())) {
  431. edgeList.add(icws.getModel());
  432. }
  433. }
  434. //aggregate all objects
  435. ArrayList<AbstractCanvasObject> objects = new ArrayList<AbstractCanvasObject>();
  436. for(Edge e : edgeList) {
  437. AbstractCanvasObject a = e.getA();
  438. AbstractCanvasObject b = e.getB();
  439. if(!objects.contains(a)) {
  440. objects.add(a);
  441. }
  442. if(!objects.contains(b)) {
  443. objects.add(b);
  444. }
  445. }
  446. this.minModel = new MinimumModel(objects, edgeList);
  447. if(this.parent != null && this.parent.getParent() != null) {
  448. this.parent.recalculateMinModel(this);
  449. }
  450. }
  451. /**
  452. * revalidate this min model after a subholon was removed
  453. */
  454. public void revalidateMinModel(Holon removed) {
  455. if(this.parent == null)
  456. return;
  457. //remove all objects that were part of the removed holon
  458. ArrayList<AbstractCanvasObject> objects = this.getAllObjects();
  459. ArrayList<AbstractCanvasObject> objectsToRemove = removed.getAllObjects();
  460. objects.removeAll(objectsToRemove);
  461. ArrayList<Edge> edges = new ArrayList<>();
  462. for(IntermediateCableWithState icws : this.minModel.getEdgeList()) {
  463. Edge e = icws.getModel();
  464. AbstractCanvasObject a = e.getA();
  465. AbstractCanvasObject b = e.getB();
  466. if(!objectsToRemove.contains(a) && !objectsToRemove.contains(b)) {
  467. edges.add(e);
  468. }
  469. }
  470. //remove all unnecessary objects and edges
  471. removeDeadEnds(objects, edges);
  472. this.minModel = new MinimumModel(objects, edges);
  473. if(this.parent != null) {
  474. this.parent.revalidateMinModel(removed);
  475. }
  476. }
  477. /**
  478. * remove all switches and nodes which are only connected by a single edge
  479. * @param objects
  480. * @param edges
  481. */
  482. private void removeDeadEnds(List<AbstractCanvasObject> objects, List<Edge> edges) {
  483. // Save for each objects which edges are associated with it
  484. HashMap<AbstractCanvasObject, List<Edge>> map = new HashMap<>();
  485. for(Edge e : edges) {
  486. AbstractCanvasObject a = e.getA();
  487. AbstractCanvasObject b = e.getB();
  488. List<Edge> as = map.getOrDefault(a, new ArrayList<>());
  489. as.add(e);
  490. map.put(a, as);
  491. List<Edge> bs = map.getOrDefault(b, new ArrayList<>());
  492. bs.add(e);
  493. map.put(b, bs);
  494. }
  495. // remove all objects which are only associated by one edge, also remove the associated edge
  496. boolean b = false;
  497. for(AbstractCanvasObject aco : map.keySet()) {
  498. if(aco instanceof HolonObject) {
  499. continue;
  500. }
  501. List<Edge> list = map.get(aco);
  502. if(list.size() == 1) {
  503. objects.remove(aco);
  504. edges.remove(list.get(0));
  505. b = true;
  506. } else if(list.size() < 1) {
  507. objects.remove(aco);
  508. }
  509. }
  510. if(b) {
  511. //there was a dead end -> we could have created a new dead end
  512. removeDeadEnds(objects, edges);
  513. }
  514. }
  515. private AbstractCanvasObject getMin(HashMap<AbstractCanvasObject, Float> dist) {
  516. float min = Float.MAX_VALUE;
  517. AbstractCanvasObject key = null;
  518. for(AbstractCanvasObject aco : dist.keySet()) {
  519. float f = dist.get(aco);
  520. if(f < min) {
  521. min = f;
  522. key = aco;
  523. }
  524. }
  525. return key;
  526. }
  527. public void revalidateMinModelAfterLoad() {
  528. if(this.childHolons.size() == 0) {
  529. revalidateMinModelAfterLoad2();
  530. } else {
  531. List<Holon> list = List.copyOf(this.childHolons);
  532. for(Holon child : list) {
  533. child.revalidateMinModelAfterLoad();
  534. }
  535. }
  536. }
  537. public void revalidateMinModelAfterLoad2() {
  538. if(this.parent == null)
  539. return;
  540. ArrayList<AbstractCanvasObject> list = new ArrayList<AbstractCanvasObject>();
  541. list.add(this.holonObject);
  542. this.minModel = new MinimumModel(list, new ArrayList<Edge>());
  543. for(int i=0; i< this.childHolons.size(); i++) {
  544. Holon child = this.childHolons.remove(0);
  545. // System.out.println("hu");
  546. if(this.model.checkHolonObjectsAreConnected(this, child)) {
  547. this.merge(child);
  548. }
  549. }
  550. if(this.parent != null) {
  551. this.parent.revalidateMinModelAfterLoad2();
  552. }
  553. }
  554. /**
  555. * returns the holon which uses the specified path if it is included in min model, otherwise null
  556. */
  557. public Holon containsPath(ArrayList<Edge> path, Holon requester) {
  558. if(this.minModel.containsPath(path) || this.parent == null) {
  559. for(Holon child : this.childHolons) {
  560. if(child.equals(requester))
  561. continue;
  562. Holon h = child.containsPath(path, this);
  563. if(h != null) {
  564. return h;
  565. }
  566. }
  567. return this;
  568. }
  569. for(Edge e : path) {
  570. AbstractCanvasObject a = e.getA();
  571. AbstractCanvasObject b = e.getB();
  572. if(a instanceof HolonObject && this.childHolons.contains(((HolonObject) a).holon))
  573. return ((HolonObject) a).holon;
  574. if(b instanceof HolonObject && this.childHolons.contains(((HolonObject) b).holon))
  575. return ((HolonObject) b).holon;
  576. if(this.getAllObjects().contains(a) || this.getAllObjects().contains(b))
  577. return this;
  578. }
  579. return null;
  580. }
  581. public boolean containsObject(AbstractCanvasObject aco) {
  582. return false;
  583. }
  584. /**
  585. * checks whether the requester can run without this holon (none of the paths inside the requesters model is occupied by this model)
  586. * @param requester
  587. * @return
  588. */
  589. public boolean canRunIndependent(Holon requester) {
  590. if(this.parent == null)
  591. return true;
  592. ArrayList<AbstractCanvasObject> objects = new ArrayList<AbstractCanvasObject>();
  593. objects.addAll(requester.getMinimumModel().getHolonObjectList());
  594. objects.addAll(requester.getMinimumModel().getNodeList());
  595. objects.addAll(requester.getMinimumModel().getSwitchList());
  596. for(Holon child : this.childHolons) {
  597. if(child.equals(requester))
  598. continue;
  599. ArrayList<Edge> path = this.holonControlUnit.getHierarchyController().getPathsToChildren().get(child);
  600. ArrayList<AbstractCanvasObject> pathObjects = new ArrayList<AbstractCanvasObject>();
  601. for(Edge e : path) {
  602. AbstractCanvasObject a = e.getA();
  603. AbstractCanvasObject b = e.getB();
  604. if(!pathObjects.contains(a))
  605. pathObjects.add(a);
  606. if(!pathObjects.contains(b))
  607. pathObjects.add(b);
  608. }
  609. for(AbstractCanvasObject aco : pathObjects) {
  610. if(objects.contains(aco))
  611. return false;
  612. }
  613. }
  614. return true;
  615. }
  616. public boolean canRunIndependent(String requester) {
  617. return this.canRunIndependent(this.model.getHolonsByID().get(requester));
  618. }
  619. public boolean isASuperiorHolon(String holon) {
  620. return this.parent != null ? (this.parent.getUniqueID().equals(holon) || this.parent.isASuperiorHolon(holon)) : false;
  621. }
  622. public boolean isASubordinatedHolon(Holon parent) {
  623. if(parent == null)
  624. return true;
  625. for(Holon child: this.childHolons) {
  626. if(child.getUniqueID().equals(parent.getUniqueID()) || child.isASubordinatedHolon(parent))
  627. return true;
  628. }
  629. return false;
  630. }
  631. public int getMergeCounter() {
  632. return mergeCounter;
  633. }
  634. public int getSplitCounter() {
  635. return splitCounter;
  636. }
  637. public void incSplitCounter() {
  638. this.splitCounter++;
  639. }
  640. public void incMergeCounter() {
  641. this.mergeCounter++;
  642. }
  643. public int getIndeCounter() {
  644. return indeCounter;
  645. }
  646. public void incIndeCounter() {
  647. this.indeCounter++;
  648. }
  649. public int getKickCounter() {
  650. return splitCounter;
  651. }
  652. public void incKickCounter() {
  653. this.kickCounter++;
  654. }
  655. public int[] getStateCounter() {
  656. return this.stateCounter;
  657. }
  658. public void countState(float dev) {
  659. if(Math.abs(dev) <= 1-OptimizationManager.POWER_THRESHOLD_COMFORT) {
  660. this.stateCounter[0]++;
  661. } else if(Math.abs(dev) <= 1-OptimizationManager.POWER_THRESHOLD_STABILITY) {
  662. this.stateCounter[1]++;
  663. } else {
  664. this.stateCounter[2]++;
  665. }
  666. }
  667. public int stateEval() {
  668. StateIndicator s = this.holonControlUnit.getStateEstimator().getStateIndicator();
  669. return s == StateIndicator.DESIRED ? 0 : s == StateIndicator.ENDANGERED ? 1 : 2;
  670. }
  671. }