Advertisement
VladNitu

dianaMakeSpanLinearAccClean

Apr 25th, 2023
97
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 8.36 KB | None | 0 0
  1. #include <iostream>
  2. #include <vector>
  3. #include <queue>
  4. #include <climits>
  5. #include <algorithm>
  6. #include <fstream>
  7.  
  8. #define MAXN 100000// maximum number of nodes in graph
  9. #define NMAX 100 + 5
  10. #define TMAX 1000 + 5
  11. using namespace std;
  12.  
  13.  
  14. int n, m, k;
  15. int start, destination, weight;
  16. int startOfNewAgent;
  17. int vertex, steps, timeStamp;
  18.  
  19.  
  20. std::vector<int> agents;
  21. std::vector<std::vector<std::pair<int, int>>> targetPath;
  22.  
  23. // edges in the original graph
  24. int edges[NMAX][NMAX];
  25.  
  26. int viz[NMAX][TMAX];
  27.  
  28.  
  29. struct Edge
  30. {
  31. Edge(int _a, int _b, int _c, int _f, int _w) {
  32. a = _a; b = _b; c = _c; f = _f; w = _w;
  33. }
  34. ~Edge() { };
  35. int a; //from
  36. int b; //to
  37. int c; //capacity
  38. int f; //flow
  39. int w; //weight
  40. Edge* r;
  41. };
  42.  
  43.  
  44. const int MAX_DIST = 2000000; //do not choose INT_MAX because you are adding weights to it
  45. std::vector<Edge*> adj[MAXN];
  46. int distances[MAXN];
  47. Edge* parents[MAXN];
  48.  
  49. int nodecount = 1000;
  50. int source;
  51. int sink;
  52.  
  53. std::vector<std::vector<int>> layer_on_timestamp;
  54. std::vector<std::vector<int>> layer_on_double_timestamp;
  55. std::vector<int> sinks;
  56.  
  57. std::vector<int> possibleMakeSpan;
  58.  
  59. // bellman - ford
  60. bool find_path(int from, int to, std::vector<Edge*>& output)
  61. {
  62. std::fill(distances, distances+nodecount, MAX_DIST);
  63. std::fill(parents, parents+nodecount, (Edge*)0);
  64. distances[from] = 0;
  65.  
  66. bool updated = true;
  67. while(updated)
  68. {
  69. updated = false;
  70. for(int j = 0; j < nodecount; ++j)
  71. for(int k = 0; k < (int)adj[j].size(); ++k){
  72. Edge* e = adj[j][k];
  73. if( e->f >= e->c ) continue;
  74. if( distances[e->b] > distances[e->a] + e->w )
  75. {
  76. //std::cerr << distances[e->b] << " " << distances[e->a] << " " << e->w << std::endl;
  77. distances[e->b] = distances[e->a] + e->w;
  78. parents[e->b] = e;
  79. updated = true;
  80. }
  81. }
  82. }
  83. output.clear();
  84. if(distances[to] == MAX_DIST) return false;
  85. int cur = to;
  86. while(parents[cur])
  87. {
  88. output.push_back(parents[cur]);
  89. cur = parents[cur]->a;
  90. }
  91. return true;
  92. }
  93.  
  94.  
  95. // MAX FLOW MIN COST IMPLEMENTATION
  96. int min_cost_max_flow(int source, int sink)
  97. {
  98. int total_cost = 0;
  99.  
  100. int totalFlow = 0;
  101. std::vector<Edge*> p;
  102. while(find_path(source, sink, p))
  103. {
  104. int flow = INT_MAX;
  105. for(int i = 0; i < p.size(); ++i)
  106. if(p[i]->c - p[i]->f < flow) flow = p[i]->c - p[i]->f;
  107.  
  108. int cost = 0;
  109. for(int i = 0; i < p.size(); ++i) {
  110. cost += p[i]->w;
  111. p[i]->f += flow;
  112. p[i]->r->f -= flow;
  113. }
  114. cost *= flow; //cost per flow
  115. total_cost += cost;
  116. totalFlow += flow;
  117. }
  118.  
  119. return totalFlow;
  120. }
  121.  
  122. int run(int source, int sink) {
  123. const auto max_flow = min_cost_max_flow(source, sink);
  124. for (int i = 0; i < nodecount; ++i) {
  125.  
  126. for (unsigned int j = 0; j < adj[i].size(); ++j)
  127. delete adj[i][j];
  128. adj[i].clear();
  129. }
  130.  
  131. return max_flow;
  132. }
  133.  
  134.  
  135. void add_edge(int a, int b, int c, int w)
  136. {
  137. Edge* e = new Edge(a, b, c, 0, w);
  138. Edge* re = new Edge(b, a, 0, 0, -w);
  139. e->r = re;
  140. re->r = e;
  141. adj[a].push_back(e);
  142. adj[b].push_back(re);
  143. }
  144.  
  145.  
  146. void reset() {
  147. sinks.clear();
  148. for (int i = 0; i < NMAX; ++i)
  149. for (int j = 0; j < NMAX; ++j)
  150. viz[i][j] = false;
  151.  
  152. layer_on_timestamp.clear();
  153. layer_on_double_timestamp.clear();
  154.  
  155. }
  156. void constructGraph(int max_timestamp) {
  157.  
  158.  
  159. // construct graph
  160. source = 0;
  161. sink = 1;
  162.  
  163. int id = 2;
  164.  
  165. reset();
  166.  
  167. layer_on_timestamp.resize(TMAX + 1, vector<int>(NMAX + 1, -1));
  168. layer_on_double_timestamp.resize(TMAX + 1, vector<int>(NMAX + 1, -1));
  169. sinks.resize(k + 1);
  170.  
  171. // create the sink and the corresponding edges
  172. for(int target = 0; target < k; target ++) {
  173. sinks[target] = id ++;
  174. // add edges to the sink from the target
  175. add_edge(sinks[target], sink, 1, 0);
  176. }
  177.  
  178. // construct rest of the matrix
  179. std::queue<std::pair<int, int>> queue; // node, timestamp pair
  180.  
  181. // go through all the agents and create edges from the source
  182. for(int i = 0; i < k ; i++) {
  183. queue.push(std::make_pair(agents[i], 0));
  184. layer_on_timestamp[0][agents[i]] = id ++;
  185. add_edge(source, layer_on_timestamp[0][agents[i]], 1, 0);
  186. }
  187.  
  188. while(!queue.empty()) {
  189. std::pair<int, int> current = queue.front();
  190. queue.pop();
  191.  
  192. int node = current.first;
  193. int timestamp = current.second;
  194.  
  195. if (timestamp > max_timestamp || viz[node][timestamp])
  196. continue;
  197.  
  198. viz[node][timestamp] = 1;
  199.  
  200. if (layer_on_double_timestamp[timestamp][node] == -1)
  201. layer_on_double_timestamp[timestamp][node] = id ++;
  202.  
  203.  
  204. // stay in place
  205. if(timestamp + 1 <= max_timestamp) {
  206. if(layer_on_timestamp[timestamp + 1][node] == -1)
  207. layer_on_timestamp[timestamp + 1][node] = id ++;
  208.  
  209. add_edge(layer_on_double_timestamp[timestamp][node], layer_on_timestamp[timestamp + 1][node], 1,
  210. 1);
  211. queue.push(std::make_pair(node, timestamp + 1));
  212. }
  213.  
  214. for (int i = 0; i < n; i++) {
  215. int forward = edges[node][i];
  216.  
  217. if (timestamp + forward <= max_timestamp && forward != 0) {
  218. if (layer_on_timestamp[timestamp + forward][i] == -1)
  219. layer_on_timestamp[timestamp + forward][i] = id ++;
  220.  
  221. add_edge(layer_on_double_timestamp[timestamp][node], layer_on_timestamp[timestamp + forward][i], 1,
  222. forward);
  223. queue.push(std::make_pair(i, timestamp + forward));
  224. }
  225. }
  226.  
  227. }
  228.  
  229. // create edges from targets to the sink target
  230. for(int target = 0; target < k; target ++) {
  231. int sink_of_target = sinks[target];
  232.  
  233. std::vector<std::pair<int, int>> path = targetPath[target];
  234.  
  235. // position -> vertex, timestamp
  236. for (auto position: path) {
  237. if (layer_on_double_timestamp[position.second][position.first] == -1)
  238. layer_on_double_timestamp[position.second][position.first] = id ++;
  239.  
  240. add_edge(layer_on_double_timestamp[position.second][position.first], sink_of_target, 1, 0);
  241. }
  242.  
  243. std::pair<int, int> last_node = path.back();
  244. for(int i = last_node.second + 1; i <= max_timestamp; i++) {
  245. if (layer_on_double_timestamp[i][last_node.first] == -1)
  246. layer_on_double_timestamp[i][last_node.first] = id ++;
  247.  
  248. add_edge(layer_on_double_timestamp[i][last_node.first], sink_of_target, 1, 0);
  249. }
  250. }
  251.  
  252. for (int t = 0; t <= max_timestamp; ++t)
  253. for (int i = 0; i < n; ++i)
  254. if (layer_on_timestamp[t][i] != -1 && layer_on_double_timestamp[t][i] != -1) {
  255. add_edge(layer_on_timestamp[t][i], layer_on_double_timestamp[t][i], 1, 0);
  256. }
  257.  
  258.  
  259. nodecount = id + 5;
  260. }
  261.  
  262. int main() {
  263. //std::ifstream cin("date.in");
  264. // freopen("date.in" , "r", stdin);
  265.  
  266. // read vertex num, edges num and k (agent/target count)
  267. std::cin >> n >> m >> k;
  268.  
  269. // read graph
  270. for(int i = 0; i < m; i++) {
  271. std::cin >> start >> destination >> weight;
  272.  
  273. // directed graph add just one time
  274. edges[start][destination] = weight;
  275. }
  276.  
  277. // see where the agents are starting -> value of index for each
  278. for(int i = 0; i < k; i++) {
  279. std::cin >> startOfNewAgent;
  280. agents.push_back(startOfNewAgent);
  281. }
  282.  
  283. // see the steps that each target makes -> (vertex, time)
  284. for(int i = 0; i < k; i++) {
  285. std::cin >> steps;
  286.  
  287. std::vector<std::pair<int, int>> path;
  288. for (int j = 0; j < steps; j++) {
  289. std::cin >> vertex >> timeStamp;
  290. path.push_back(std::make_pair(vertex, timeStamp));
  291.  
  292. }
  293.  
  294. targetPath.push_back(path);
  295. }
  296.  
  297. int maxTime = -1;
  298.  
  299. for (int t = 1; t <= TMAX; ++t) {
  300. constructGraph(t);
  301. int ans = run(0, 1);
  302. if (ans == k) // cuplaj
  303. {
  304. maxTime = t;
  305. break;
  306. }
  307. }
  308.  
  309. cout << maxTime << '\n';
  310. return 0;
  311. }
  312.  
  313.  
  314.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement