-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathFibre optique - brute force.cpp
132 lines (111 loc) · 3.05 KB
/
Fibre optique - brute force.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
#include "bits/stdc++.h"
using namespace std;
int N;
vector<pair<int, int>> cables;
int compute_tree_size(int root, vector<vector<int>> &p, set<int> &a) {
int res = 1;
a.insert(root);
for (auto &c : p[root]) {
if (a.find(c) == a.end()) res += compute_tree_size(c, p, a);
}
a.erase(root);
return res;
}
int brute_force() {
vector<vector<int>> p(N, vector<int>(0));
for (auto &c : cables) {
p[c.first].push_back(c.second);
p[c.second].push_back(c.first);
}
int maxi = 0;
for (int i = 0; i < N; i++) {
int max_child_size = 0;
set<int> s;
s.insert(i);
for (auto &j : p[i])
max_child_size = max(max_child_size, compute_tree_size(j, p, s));
maxi = max(maxi, N - max_child_size);
}
return maxi;
}
int c_w(int a, int b, vector<vector<pair<int, int>>> &p) {
int index = find_if(p[a].begin(), p[a].end(),
[b](auto &x) { return x.first == b; }) -
p[a].begin();
// already computed
if (p[a][index].second) return p[a][index].second;
// compute if not already computed
int res = 1;
for (auto &c : p[b]) {
if (c.first != a) res += c_w(b, c.first, p);
}
p[a][index].second = res;
return p[a][index].second;
}
int solve() {
vector<vector<pair<int, int>>> p(N, vector<pair<int, int>>(0));
for (auto &c : cables) {
p[c.first].emplace_back(c.second, 0);
p[c.second].emplace_back(c.first, 0);
}
// compute edges weights
for (int i = 0; i < N; i++) {
for (auto &d : p[i]) {
c_w(i, d.first, p);
}
}
int res = 0;
for (int i = 0; i < N; i++) {
auto maxi = max_element(p[i].begin(), p[i].end(), [](auto &l, auto &r) {
return l.second < r.second;
})->second;
// cout << n - maxi << " ";
res = max(res, N - maxi);
}
return res;
}
void generate_test_case(int min, int max) {
// Generate random number of PCs (between 2 and 10)
N = rand() % (max - 1) + min;
// Generate cables connecting PCs
cables.clear();
for (int i = 0; i < N - 1; ++i) {
int pc1 = i;
int pc2 = rand() % (N - i - 1) + i + 1; // Ensure PC2 is greater than PC1
cables.push_back({pc1, pc2});
}
}
void print() {
// Print test case and answer
cout << N << "\n";
for (auto &cable : cables) {
cout << cable.first << " " << cable.second << "\n";
}
}
void print(int answer, int found) {
// Print test case and answer
print();
cout << "Answer: " << answer << "\n";
cout << "Found:" << found << "\n";
}
int main(int argc, char *argv[]) {
// Seed random number generator with current time
srand(time(NULL));
if (argc != 3) {
cout << "Usage: " << argv[0] << " <min_pcs> <max_pcs>"
<< "\n";
return 1;
}
int min_pcs = atoi(argv[1]);
int max_pcs = atoi(argv[2]);
int a = 0, b = 0, i = 1;
cout << 0;
while (a == b && i < 1e5) {
cout << "\r" << i++;
generate_test_case(min_pcs, max_pcs);
a = brute_force();
b = solve();
}
print(a, b);
return 0;
}