graph_manager.hpp 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472
  1. /**
  2. * @file tests/boost_graph/graph_manager.hpp
  3. * @author The PARADEVS Development Team
  4. * See the AUTHORS or Authors.txt file
  5. */
  6. /*
  7. * PARADEVS - the multimodeling and simulation environment
  8. * This file is a part of the PARADEVS environment
  9. *
  10. * Copyright (C) 2013 ULCO http://www.univ-litoral.fr
  11. *
  12. * This program is free software: you can redistribute it and/or modify
  13. * it under the terms of the GNU General Public License as published by
  14. * the Free Software Foundation, either version 3 of the License, or
  15. * (at your option) any later version.
  16. *
  17. * This program is distributed in the hope that it will be useful,
  18. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  19. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  20. * GNU General Public License for more details.
  21. *
  22. * You should have received a copy of the GNU General Public License
  23. * along with this program. If not, see <http://www.gnu.org/licenses/>.
  24. */
  25. #ifndef __TESTS_BOOST_GRAPH_GRAPH_MANAGER_HPP
  26. #define __TESTS_BOOST_GRAPH_GRAPH_MANAGER_HPP 1
  27. #include <boost/graph/adjacency_list.hpp>
  28. #include <common/scheduler/HeapScheduler.hpp>
  29. #include <common/scheduler/VectorScheduler.hpp>
  30. #include <pdevs/Coordinator.hpp>
  31. #include <pdevs/GraphManager.hpp>
  32. #include <pdevs/Simulator.hpp>
  33. #include <tests/boost_graph/models.hpp>
  34. namespace paradevs { namespace tests { namespace boost_graph {
  35. struct VertexProperties
  36. {
  37. int _index;
  38. double _weight;
  39. DynamicsType _type;
  40. VertexProperties() : _index(0), _weight(0), _type(NORMAL_PIXEL)
  41. { }
  42. VertexProperties(int index, double weight, DynamicsType type) :
  43. _index(index), _weight(weight), _type(type)
  44. { }
  45. };
  46. struct EdgeProperties
  47. {
  48. double _weight;
  49. EdgeProperties() : _weight(0)
  50. { }
  51. EdgeProperties(double weight) : _weight(weight)
  52. { }
  53. };
  54. typedef boost::adjacency_list < boost::vecS, boost::vecS, boost::directedS,
  55. VertexProperties, EdgeProperties> Graph;
  56. typedef std::vector < Graph > Graphs;
  57. typedef std::pair < int, int > Edge;
  58. typedef std::vector < Edge > Edges;
  59. typedef Edges OutputEdges;
  60. typedef Edges InputEdges;
  61. typedef std::vector < OutputEdges > OutputEdgeList;
  62. typedef std::vector < InputEdges > InputEdgeList;
  63. typedef std::pair < int, int > Port;
  64. typedef std::pair < Port, Port > Connection;
  65. typedef std::vector < Connection > Connections;
  66. struct GraphParameters
  67. {
  68. Graph _graph;
  69. InputEdges _input_edges;
  70. OutputEdges _output_edges;
  71. GraphParameters(const Graph& graph,
  72. const InputEdges& input_edges,
  73. const OutputEdges& output_edges) :
  74. _graph(graph), _input_edges(input_edges), _output_edges(output_edges)
  75. { }
  76. };
  77. template < class Parameters >
  78. class FlatGraphManager :
  79. public paradevs::pdevs::GraphManager < MyTime, Parameters >
  80. {
  81. public:
  82. FlatGraphManager(common::Coordinator < MyTime >* coordinator,
  83. const Parameters& parameters) :
  84. paradevs::pdevs::GraphManager < MyTime, Parameters >(
  85. coordinator, parameters)
  86. { }
  87. virtual ~FlatGraphManager()
  88. {
  89. for (TopSimulators::const_iterator it = _top_simulators.begin();
  90. it != _top_simulators.end(); ++it) {
  91. delete it->second;
  92. }
  93. for (NormalSimulators::const_iterator it = _normal_simulators.begin();
  94. it != _normal_simulators.end(); ++it) {
  95. delete it->second;
  96. }
  97. }
  98. void build_flat_graph(const Graph& g)
  99. {
  100. Graph::vertex_iterator vertexIt, vertexEnd;
  101. boost::tie(vertexIt, vertexEnd) = boost::vertices(g);
  102. for (; vertexIt != vertexEnd; ++vertexIt)
  103. {
  104. std::ostringstream ss;
  105. ss << "a" << g[*vertexIt]._index;
  106. switch (g[*vertexIt]._type) {
  107. case TOP_PIXEL:
  108. _top_simulators[g[*vertexIt]._index] =
  109. new pdevs::Simulator <
  110. MyTime, TopPixel, TopPixelParameters >(
  111. ss.str(), TopPixelParameters());
  112. FlatGraphManager < Parameters >::add_child(
  113. _top_simulators[g[*vertexIt]._index]);
  114. break;
  115. case NORMAL_PIXEL:
  116. unsigned int n = 0;
  117. Graph::adjacency_iterator neighbourIt, neighbourEnd;
  118. boost::tie(neighbourIt, neighbourEnd) =
  119. boost::adjacent_vertices(*vertexIt, g);
  120. for (; neighbourIt != neighbourEnd; ++neighbourIt) {
  121. ++n;
  122. }
  123. _normal_simulators[g[*vertexIt]._index] =
  124. new pdevs::Simulator <
  125. MyTime, NormalPixel, NormalPixelParameters >(
  126. ss.str(), NormalPixelParameters(n));
  127. FlatGraphManager < Parameters >::add_child(
  128. _normal_simulators[g[*vertexIt]._index]);
  129. break;
  130. };
  131. }
  132. boost::tie(vertexIt, vertexEnd) = boost::vertices(g);
  133. for (; vertexIt != vertexEnd; ++vertexIt)
  134. {
  135. Graph::adjacency_iterator neighbourIt, neighbourEnd;
  136. boost::tie(neighbourIt, neighbourEnd) =
  137. boost::adjacent_vertices(*vertexIt, g);
  138. for (; neighbourIt != neighbourEnd; ++neighbourIt) {
  139. paradevs::common::Model < MyTime >* a = 0;
  140. paradevs::common::Model < MyTime >* b = 0;
  141. if (g[*vertexIt]._type == TOP_PIXEL) {
  142. a = _top_simulators[g[*vertexIt]._index];
  143. } else {
  144. a = _normal_simulators[g[*vertexIt]._index];
  145. }
  146. if (g[*neighbourIt]._type == TOP_PIXEL) {
  147. b = _top_simulators[g[*neighbourIt]._index];
  148. } else {
  149. b = _normal_simulators[g[*neighbourIt]._index];
  150. }
  151. FlatGraphManager < Parameters >::add_link(b, "out", a, "in");
  152. }
  153. }
  154. }
  155. protected:
  156. typedef std::map < int, pdevs::Simulator <
  157. MyTime, TopPixel,
  158. TopPixelParameters >* > TopSimulators;
  159. typedef std::map < int, pdevs::Simulator <
  160. MyTime, NormalPixel,
  161. NormalPixelParameters>* > NormalSimulators;
  162. TopSimulators _top_simulators;
  163. NormalSimulators _normal_simulators;
  164. };
  165. class BuiltFlatGraphManager :
  166. public FlatGraphManager < GraphParameters >
  167. {
  168. public:
  169. BuiltFlatGraphManager(common::Coordinator < MyTime >* coordinator,
  170. const GraphParameters& parameters) :
  171. FlatGraphManager < GraphParameters >(
  172. coordinator, parameters)
  173. {
  174. build_flat_graph(parameters._graph);
  175. // input
  176. for (Edges::const_iterator it = parameters._input_edges.begin();
  177. it != parameters._input_edges.end(); ++it) {
  178. std::ostringstream ss_in;
  179. ss_in << "in_" << it->first;
  180. BuiltFlatGraphManager::add_link(coordinator, ss_in.str(),
  181. _normal_simulators[it->second],
  182. "in");
  183. }
  184. // output
  185. for (Edges::const_iterator it = parameters._output_edges.begin();
  186. it != parameters._output_edges.end(); ++it) {
  187. std::ostringstream ss_out;
  188. ss_out << "out_" << it->second;
  189. BuiltFlatGraphManager::add_link(_normal_simulators[it->first],
  190. "out", coordinator, ss_out.str());
  191. }
  192. }
  193. virtual ~BuiltFlatGraphManager()
  194. { }
  195. };
  196. template < class GraphBuilder >
  197. class InBuildFlatGraphManager :
  198. public FlatGraphManager < paradevs::common::NoParameters >
  199. {
  200. public:
  201. InBuildFlatGraphManager(common::Coordinator < MyTime >* coordinator,
  202. const paradevs::common::NoParameters& parameters) :
  203. FlatGraphManager < paradevs::common::NoParameters >(
  204. coordinator, parameters)
  205. {
  206. GraphBuilder builder;
  207. Graphs graphs;
  208. InputEdgeList input_edges;
  209. OutputEdgeList output_edges;
  210. Connections parent_connections;
  211. builder.build(graphs, input_edges, output_edges, parent_connections);
  212. build_flat_graph(graphs.front());
  213. }
  214. virtual ~InBuildFlatGraphManager()
  215. { }
  216. };
  217. class FlatGraphBuilder
  218. {
  219. public:
  220. FlatGraphBuilder()
  221. { }
  222. void build(Graphs& graphs, InputEdgeList& /* input_edges */,
  223. OutputEdgeList& /* output_edges */,
  224. Connections& /* parent_connections */)
  225. {
  226. Graph graph;
  227. Graph::vertex_descriptor v0 = boost::add_vertex(graph);
  228. Graph::vertex_descriptor v1 = boost::add_vertex(graph);
  229. Graph::vertex_descriptor v2 = boost::add_vertex(graph);
  230. Graph::vertex_descriptor v3 = boost::add_vertex(graph);
  231. Graph::vertex_descriptor v4 = boost::add_vertex(graph);
  232. Graph::vertex_descriptor v5 = boost::add_vertex(graph);
  233. Graph::vertex_descriptor v6 = boost::add_vertex(graph);
  234. Graph::vertex_descriptor v7 = boost::add_vertex(graph);
  235. Graph::vertex_descriptor v8 = boost::add_vertex(graph);
  236. Graph::vertex_descriptor v9 = boost::add_vertex(graph);
  237. Graph::vertex_descriptor v10 = boost::add_vertex(graph);
  238. boost::add_edge(v0, v1, 1, graph);
  239. boost::add_edge(v0, v2, 1, graph);
  240. boost::add_edge(v0, v3, 1, graph);
  241. boost::add_edge(v1, v2, 1, graph);
  242. boost::add_edge(v1, v4, 1, graph);
  243. boost::add_edge(v1, v5, 1, graph);
  244. boost::add_edge(v1, v6, 1, graph);
  245. boost::add_edge(v2, v6, 1, graph);
  246. boost::add_edge(v2, v3, 1, graph);
  247. boost::add_edge(v3, v9, 1, graph);
  248. boost::add_edge(v3, v10, 1, graph);
  249. boost::add_edge(v4, v5, 1, graph);
  250. boost::add_edge(v5, v6, 1, graph);
  251. boost::add_edge(v4, v7, 1, graph);
  252. boost::add_edge(v4, v8, 1, graph);
  253. boost::add_edge(v7, v8, 1, graph);
  254. boost::add_edge(v9, v10, 1, graph);
  255. graph[v6] = VertexProperties(6, 1, TOP_PIXEL);
  256. graph[v8] = VertexProperties(8, 1, TOP_PIXEL);
  257. graph[v10] = VertexProperties(10, 1, TOP_PIXEL);
  258. graph[v0] = VertexProperties(0, 1, NORMAL_PIXEL);
  259. graph[v1] = VertexProperties(1, 1, NORMAL_PIXEL);
  260. graph[v2] = VertexProperties(2, 1, NORMAL_PIXEL);
  261. graph[v3] = VertexProperties(3, 1, NORMAL_PIXEL);
  262. graph[v4] = VertexProperties(4, 1, NORMAL_PIXEL);
  263. graph[v5] = VertexProperties(5, 1, NORMAL_PIXEL);
  264. graph[v7] = VertexProperties(7, 1, NORMAL_PIXEL);
  265. graph[v9] = VertexProperties(9, 1, NORMAL_PIXEL);
  266. graphs.push_back(graph);
  267. }
  268. };
  269. template < class GraphBuilder >
  270. class HierarchicalGraphManager :
  271. public paradevs::pdevs::GraphManager < MyTime,
  272. paradevs::common::NoParameters >
  273. {
  274. public:
  275. HierarchicalGraphManager(common::Coordinator < MyTime >* coordinator,
  276. const paradevs::common::NoParameters& parameters) :
  277. paradevs::pdevs::GraphManager < MyTime,
  278. paradevs::common::NoParameters >(
  279. coordinator, parameters)
  280. {
  281. GraphBuilder graph_builder;
  282. Graphs graphs;
  283. InputEdgeList input_edges;
  284. OutputEdgeList output_edges;
  285. Connections parent_connections;
  286. graph_builder.build(graphs, input_edges, output_edges,
  287. parent_connections);
  288. // build coordinators (graphs)
  289. for (unsigned int i = 0; i < graphs.size(); ++i) {
  290. Coordinator* coordinator = 0;
  291. std::ostringstream ss;
  292. ss << "S" << i;
  293. coordinator =
  294. new Coordinator(ss.str(), paradevs::common::NoParameters(),
  295. GraphParameters(graphs[i], input_edges[i],
  296. output_edges[i]));
  297. _coordinators.push_back(coordinator);
  298. HierarchicalGraphManager < GraphBuilder >::add_child(
  299. coordinator);
  300. }
  301. // builds internal connections (edges)
  302. for (Connections::const_iterator it = parent_connections.begin();
  303. it != parent_connections.end(); ++it) {
  304. const Connection& connection = *it;
  305. std::ostringstream ss_out;
  306. std::ostringstream ss_in;
  307. ss_out << "out_" << connection.first.second;
  308. ss_in << "in_" << connection.second.second;
  309. HierarchicalGraphManager < GraphBuilder >::add_link(
  310. _coordinators[connection.first.first], ss_out.str(),
  311. _coordinators[connection.second.first], ss_in.str());
  312. }
  313. }
  314. virtual ~HierarchicalGraphManager()
  315. {
  316. for (Coordinators::const_iterator it = _coordinators.begin();
  317. it != _coordinators.end(); ++it) {
  318. delete *it;
  319. }
  320. }
  321. private:
  322. typedef paradevs::pdevs::Coordinator < MyTime,
  323. common::scheduler::VectorScheduler <
  324. MyTime >,
  325. BuiltFlatGraphManager,
  326. common::NoParameters,
  327. GraphParameters > Coordinator;
  328. typedef std::vector < Coordinator* > Coordinators;
  329. Coordinators _coordinators;
  330. };
  331. class HierarchicalGraphBuilder
  332. {
  333. public:
  334. HierarchicalGraphBuilder()
  335. { }
  336. void build(Graphs& graphs, InputEdgeList& input_edges,
  337. OutputEdgeList& output_edges, Connections& parent_connections)
  338. {
  339. // S1
  340. {
  341. Graph graph;
  342. Graph::vertex_descriptor v1 = boost::add_vertex(graph);
  343. Graph::vertex_descriptor v2 = boost::add_vertex(graph);
  344. Graph::vertex_descriptor v4 = boost::add_vertex(graph);
  345. Graph::vertex_descriptor v5 = boost::add_vertex(graph);
  346. Graph::vertex_descriptor v6 = boost::add_vertex(graph);
  347. Graph::vertex_descriptor v7 = boost::add_vertex(graph);
  348. Graph::vertex_descriptor v8 = boost::add_vertex(graph);
  349. boost::add_edge(v1, v2, 1, graph);
  350. boost::add_edge(v1, v4, 1, graph);
  351. boost::add_edge(v1, v5, 1, graph);
  352. boost::add_edge(v1, v6, 1, graph);
  353. boost::add_edge(v2, v6, 1, graph);
  354. boost::add_edge(v4, v5, 1, graph);
  355. boost::add_edge(v5, v6, 1, graph);
  356. boost::add_edge(v4, v7, 1, graph);
  357. boost::add_edge(v4, v8, 1, graph);
  358. boost::add_edge(v7, v8, 1, graph);
  359. graph[v6] = VertexProperties(6, 1, TOP_PIXEL);
  360. graph[v8] = VertexProperties(8, 1, TOP_PIXEL);
  361. graph[v1] = VertexProperties(1, 1, NORMAL_PIXEL);
  362. graph[v2] = VertexProperties(2, 1, NORMAL_PIXEL);
  363. graph[v4] = VertexProperties(4, 1, NORMAL_PIXEL);
  364. graph[v5] = VertexProperties(5, 1, NORMAL_PIXEL);
  365. graph[v7] = VertexProperties(7, 1, NORMAL_PIXEL);
  366. graphs.push_back(graph);
  367. }
  368. // S2
  369. {
  370. Graph graph;
  371. Graph::vertex_descriptor v0 = boost::add_vertex(graph);
  372. Graph::vertex_descriptor v3 = boost::add_vertex(graph);
  373. Graph::vertex_descriptor v9 = boost::add_vertex(graph);
  374. Graph::vertex_descriptor v10 = boost::add_vertex(graph);
  375. boost::add_edge(v0, v3, 1, graph);
  376. boost::add_edge(v3, v10, 1, graph);
  377. boost::add_edge(v9, v10, 1, graph);
  378. boost::add_edge(v3, v9, 1, graph);
  379. graph[v10] = VertexProperties(10, 1, TOP_PIXEL);
  380. graph[v0] = VertexProperties(0, 1, NORMAL_PIXEL);
  381. graph[v3] = VertexProperties(3, 1, NORMAL_PIXEL);
  382. graph[v9] = VertexProperties(9, 1, NORMAL_PIXEL);
  383. graphs.push_back(graph);
  384. }
  385. {
  386. // input S1
  387. input_edges.push_back(InputEdges());
  388. input_edges[0].push_back(Edge(3, 2));
  389. // input S2
  390. input_edges.push_back(InputEdges());
  391. input_edges[0].push_back(Edge(1, 0));
  392. input_edges[0].push_back(Edge(2, 0));
  393. // output S1
  394. output_edges.push_back(OutputEdges());
  395. output_edges[0].push_back(Edge(1, 0));
  396. output_edges[0].push_back(Edge(2, 0));
  397. // output S2
  398. output_edges.push_back(OutputEdges());
  399. output_edges[0].push_back(Edge(3, 2));
  400. // parent
  401. parent_connections.push_back(Connection(Port(1,1),Port(2,0)));
  402. parent_connections.push_back(Connection(Port(1,2),Port(2,0)));
  403. parent_connections.push_back(Connection(Port(2,3),Port(1,2)));
  404. }
  405. }
  406. };
  407. } } } // namespace paradevs tests boost_graph
  408. #endif