# |
Submission time |
Handle |
Problem |
Language |
Result |
Execution time |
Memory |
787469 |
2023-07-19T08:18:30 Z |
이성호(#10033) |
도로 건설 사업 (JOI13_construction) |
C++17 |
|
48 ms |
33492 KB |
#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
vector<int> cpx, cpy;
int N, M, C, x[200005], y[200005], P[200005], Q[200005], R[200005], S[200005];
vector<int> xlist[600005], ylist[600005];
struct UnionFind
{
vector<int> par;
UnionFind(int n){par.resize(n+1); for(int i=1;i<=n;i++) par[i] = i;}
int fin(int i){return i==par[i]?i:(par[i] = fin(par[i]));}
void uni(int u, int v){par[fin(u)] = fin(v);}
bool isuni(int u, int v){return fin(u) == fin(v);}
};
vector<pair<int, pair<int, int>>> edge;
vector<pair<int, pair<int, int>>> redge;
vector<pair<int, pair<int, int>>> cand;
int maxc;
int tree[600005];
const long long inf = 1e18;
void init()
{
fill(tree, tree + 600005, 0);
}
void upd(int id, int x)
{
for (int i = id; i <= maxc; i += i&-i) tree[id] += x;
}
int query(int id)
{
int ret = 0;
for (int i = id; i; i -= i&-i) ret += tree[i];
return ret;
}
int sum(int l, int r)
{
return query(r) - query(l-1);
}
int main()
{
ios::sync_with_stdio(false); cin.tie(0); cout.tie(0);
cin >> N >> M >> C;
for (int i = 1; i <= N; i++) {
cin >> x[i] >> y[i];
cpx.push_back(x[i]);
cpy.push_back(y[i]);
}
for (int i = 1; i <= M; i++) {
cin >> P[i] >> Q[i] >> R[i] >> S[i];
cpx.push_back(P[i]); cpx.push_back(R[i]);
cpy.push_back(Q[i]); cpy.push_back(S[i]);
}
sort(cpx.begin(), cpx.end());
sort(cpy.begin(), cpy.end());
for (int i = 1; i <= N; i++) {
x[i] = lower_bound(cpx.begin(), cpx.end(), x[i]) - cpx.begin() + 1;
y[i] = lower_bound(cpy.begin(), cpy.end(), y[i]) - cpy.begin() + 1;
}
for (int i = 1; i <= M; i++) {
P[i] = lower_bound(cpx.begin(), cpx.end(), P[i]) - cpx.begin() + 1;
R[i] = lower_bound(cpx.begin(), cpx.end(), R[i]) - cpx.begin() + 1;
Q[i] = lower_bound(cpy.begin(), cpy.end(), Q[i]) - cpy.begin() + 1;
S[i] = lower_bound(cpy.begin(), cpy.end(), S[i]) - cpy.begin() + 1;
}
for (int i = 1; i <= N; i++) {
xlist[x[i]].push_back(i);
ylist[y[i]].push_back(i);
}
maxc = N + 2 * M;
for (int i = 1; i <= maxc; i++) {
sort(xlist[i].begin(), xlist[i].end(), [&](int p, int q){return y[p] < y[q];});
for (int j = 0; j < (int)xlist[i].size() - 1; j++) {
edge.push_back(make_pair(cpy[y[xlist[i][j+1]]-1] - cpy[y[xlist[i][j]]-1], make_pair(xlist[i][j], xlist[i][j+1])));
}
}
for (int i = 1; i <= maxc; i++) {
sort(ylist[i].begin(), ylist[i].end(), [&](int p, int q){return x[p] < x[q];});
for (int j = 0; j < (int)ylist[i].size() - 1; j++) {
edge.push_back(make_pair(cpx[x[ylist[i][j+1]]-1] - cpx[x[ylist[i][j]]-1], make_pair(ylist[i][j], ylist[i][j+1])));
}
}
sort(edge.begin(), edge.end());
vector<vector<int>> linex(maxc+2), liney(maxc+2);
vector<vector<int>> rectx(maxc+2), recty(maxc+2);
for (int i = 0; i < (int)edge.size(); i++) {
if (x[edge[i].second.first] == x[edge[i].second.second]) {
linex[x[edge[i].second.first]].push_back(i);
}
else {
liney[y[edge[i].second.first]].push_back(i);
}
}
for (int i = 1; i <= M; i++) {
rectx[P[i]].push_back(Q[i]);
rectx[P[i]].push_back(S[i]);
rectx[R[i]+1].push_back(-Q[i]);
rectx[R[i]+1].push_back(-S[i]);
recty[Q[i]].push_back(P[i]);
recty[Q[i]].push_back(R[i]);
recty[S[i]+1].push_back(-P[i]);
recty[S[i]+1].push_back(-R[i]);
}
init();
for (int i = 1; i <= maxc; i++) {
for (int j:rectx[i]) {
if (j > 0) upd(j, 1);
else upd(-j, -1);
}
for (int j:linex[i]) {
if (sum(y[edge[j].second.first], y[edge[j].second.second]) == 0) redge.push_back(edge[j]);
}
}
init();
for (int i = 1; i <= maxc; i++) {
for (int j:recty[i]) {
if (j > 0) upd(j, 1);
else upd(-j, -1);
}
for (int j:liney[i]) {
if (sum(x[edge[j].second.first], x[edge[j].second.second]) == 0) redge.push_back(edge[j]);
}
}
sort(redge.begin(), redge.end());
UnionFind uf(N);
for (auto i:redge) {
if (uf.isuni(i.second.first, i.second.second)) continue;
cand.push_back(i);
uf.uni(i.second.first, i.second.second);
}
vector<int> weight;
for (auto i:cand) weight.push_back(i.first);
vector<long long> costs(weight.size()+1);
for (int i = 1; i <= weight.size(); i++) costs[i] = costs[i-1] + weight[i-1];
for (int i = 1; i <= C; i++) {
long long ans = inf;
long long b, k; cin >> b >> k;
for (int j = 1; j <= k; j++) {
if (weight.size() >= N - j) ans = min(ans, costs[N-j] + b * j);
}
if (ans == inf) cout << -1 << '\n';
else cout << ans << '\n';
}
}
Compilation message
construction.cpp: In function 'int main()':
construction.cpp:134:23: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<int>::size_type' {aka 'long unsigned int'} [-Wsign-compare]
134 | for (int i = 1; i <= weight.size(); i++) costs[i] = costs[i-1] + weight[i-1];
| ~~^~~~~~~~~~~~~~~~
construction.cpp:139:31: warning: comparison of integer expressions of different signedness: 'std::vector<int>::size_type' {aka 'long unsigned int'} and 'int' [-Wsign-compare]
139 | if (weight.size() >= N - j) ans = min(ans, costs[N-j] + b * j);
| ~~~~~~~~~~~~~~^~~~~~~~
# |
Verdict |
Execution time |
Memory |
Grader output |
1 |
Incorrect |
48 ms |
33492 KB |
Output isn't correct |
2 |
Halted |
0 ms |
0 KB |
- |
# |
Verdict |
Execution time |
Memory |
Grader output |
1 |
Incorrect |
48 ms |
33492 KB |
Output isn't correct |
2 |
Halted |
0 ms |
0 KB |
- |
# |
Verdict |
Execution time |
Memory |
Grader output |
1 |
Incorrect |
48 ms |
33492 KB |
Output isn't correct |
2 |
Halted |
0 ms |
0 KB |
- |
# |
Verdict |
Execution time |
Memory |
Grader output |
1 |
Incorrect |
48 ms |
33492 KB |
Output isn't correct |
2 |
Halted |
0 ms |
0 KB |
- |