QOJ.ac
QOJ
ID | Problem | Submitter | Result | Time | Memory | Language | File size | Submit time | Judge time |
---|---|---|---|---|---|---|---|---|---|
#487524 | #8793. Toilets | ucup-team4435# | WA | 2ms | 3828kb | C++20 | 7.0kb | 2024-07-22 23:01:41 | 2024-07-22 23:01:41 |
Judging History
answer
#include "bits/stdc++.h"
#define rep(i, n) for (int i = 0; i < (n); ++i)
#define rep1(i, n) for (int i = 1; i < (n); ++i)
#define rep1n(i, n) for (int i = 1; i <= (n); ++i)
#define repr(i, n) for (int i = (n) - 1; i >= 0; --i)
#define pb push_back
#define eb emplace_back
#define all(a) (a).begin(), (a).end()
#define rall(a) (a).rbegin(), (a).rend()
#define each(x, a) for (auto &x : a)
#define ar array
#define vec vector
#define range(i, n) rep(i, n)
using namespace std;
using ll = long long;
using ull = unsigned long long;
using ld = double;
using str = string;
using pi = pair<int, int>;
using pl = pair<ll, ll>;
using vi = vector<int>;
using vl = vector<ll>;
using vpl = vector<pl>;
using vpi = vector<pair<int, int>>;
using vvi = vector<vi>;
int Bit(int mask, int b) { return (mask >> b) & 1; }
template<class T>
bool ckmin(T &a, const T &b) {
if (b < a) {
a = b;
return true;
}
return false;
}
template<class T>
bool ckmax(T &a, const T &b) {
if (b > a) {
a = b;
return true;
}
return false;
}
const int INFi = 2e9;
const int N = 5e5 + 5;
const ll INF = 2e18;
void solve() {
int n, m;
ll L;
cin >> n >> m >> L;
vl x(m);
rep(i, m) cin >> x[i];
vector<ll> t(n), p(n), s(n), d(n), v(n);
rep(i, n) {
char dirs;
cin >> t[i] >> p[i] >> dirs >> d[i];
if (dirs == '+') {
v[i] = p[i] - t[i];
s[i] = 1;
} else {
v[i] = p[i] + t[i];
s[i] = -1;
}
}
rep(i, n) {
v[i] %= L;
if (v[i] < 0) v[i] += L;
}
set<pair<ll, int>> right_q, left_q;
set<pair<ll, int>> alive;
rep(i, m) {
alive.insert({x[i], i});
}
vector<pair<ll, int>> bestL(m, {INF, -1}), bestR(m, {INF, -1});
set<ar<ll, 3>> events;
ll T = 0;
auto GetPrev = [&](int i) {
auto it = alive.find({x[i], i});
if (it == alive.begin()) it = alive.end();
return prev(it)->second;
};
auto GetNext = [&](int i) {
auto it = next(alive.find({x[i], i}));
if (it == alive.end()) it = alive.begin();
return it->second;
};
auto GetPrevRQ = [&](ll x) {
auto it = right_q.lower_bound({x, 2e9});
if (it == right_q.begin()) it = right_q.end();
return *prev(it);
};
auto GetNextLQ = [&](ll x) {
auto it = left_q.lower_bound({x + 1, -1});
if (it == left_q.end()) it = left_q.begin();
return *it;
};
auto UpdateL = [&](int i) {
// left from i toilet
if (bestL[i].second != -1) {
events.erase({bestL[i].first, bestL[i].second, i});
}
int j = GetPrev(i);
ll rq = x[i] - T;
ll lq = x[j] - T;
lq %= L;
rq %= L;
if (lq < 0) lq += L;
if (rq < 0) rq += L;
ll len = rq - lq;
if (len <= 0) len += L;
// [lq, rq]
bestL[i] = {INF, -1};
if (!right_q.empty()) {
auto [qv, qi] = GetPrevRQ(rq + 1);
ll le = (rq - qv + L) % L;
if (le < len) {
bestL[i] = {T + le, -qi};
}
}
if (bestL[i].second != -1) {
events.insert({bestL[i].first, bestL[i].second, i});
}
};
auto UpdateR = [&](int i) {
// right from i toilet
if (bestR[i].second != -1) {
events.erase({bestR[i].first, bestR[i].second, i});
}
int j = GetNext(i);
ll lq = x[i] + T;
ll rq = x[j] + T;
lq %= L;
rq %= L;
if (lq < 0) lq += L;
if (rq < 0) rq += L;
ll len = rq - lq;
if (len <= 0) len += L;
// [lq, rq]
bestR[i] = {INF, -1};
if (!left_q.empty()) {
auto [qv, qi] = GetNextLQ(lq - 1);
ll le = (qv - lq + L) % L;
if (le < len) {
bestR[i] = {T + le, qi};
}
}
if (bestR[i].second != -1) {
events.insert({bestR[i].first, bestR[i].second, i});
}
};
auto AddPeople = [&](int i) {
if (s[i] == 1) {
// to right
right_q.insert({v[i], -i});
// right_q.insert({p[i] + L, i});
if (!alive.empty()) {
auto it = alive.lower_bound({p[i], -1});
if (it == alive.end()) it = alive.begin();
UpdateL(it->second);
}
} else {
left_q.insert({v[i], i});
// left_q.insert({p[i] + L, i});
if (!alive.empty()) {
auto it = alive.lower_bound({p[i] + 1, -1});
if (it == alive.begin()) it = alive.end();
it--;
UpdateR(it->second);
}
}
};
auto AddToilet = [&] (int i) {
alive.insert({x[i], i});
UpdateL(i);
UpdateR(i);
if (alive.size() != 1) {
UpdateL(GetNext(i));
UpdateR(GetPrev(i));
}
};
vector<pair<ll, ll>> ans(n);
auto DelToilet = [&] (int i, ll t3) {
int lq = -1, rq = -1;
if (alive.size() != 1) {
lq = GetPrev(i);
rq = GetNext(i);
}
alive.erase({x[i], i});
if (bestR[i].second != -1) {
events.erase({bestR[i].first, bestR[i].second, i});
bestR[i] = {INF, -1};
}
if (bestL[i].second != -1) {
events.erase({bestL[i].first, bestL[i].second, i});
bestL[i] = {INF, -1};
}
if (lq != -1) {
UpdateR(lq);
UpdateL(rq);
}
events.insert({t3, -1, i});
};
auto Do = [&](ll t2) {
assert(T <= t2);
while (T < t2) {
if (events.empty()) {
T = t2;
break;
}
auto [t1, who, whe] = *(events.begin());
if (t1 >= t2) {
T = t2;
break;
}
// cerr << t1 << ' ' << who << ' ' << whe << endl;
assert(T <= t1);
if (who == -1) {
T = t1;
events.erase(events.begin());
AddToilet(whe);
continue;
}
if (s[who] == 1) {
right_q.erase({v[who], -who});
} else {
left_q.erase({v[who], who});
}
ans[who] = {x[whe], t1};
DelToilet(whe, t1 + d[who]);
T = t1;
}
};
rep(i, n) {
Do(t[i]);
AddPeople(i);
}
Do(INF);
rep(i, n) {
cout << ans[i].first << ' ' << ans[i].second << '\n';
}
}
signed main() {
ios_base::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
cout << setprecision(15) << fixed;
int t = 1;
// cin >> t;
rep(_, t) {
solve();
}
return 0;
}
Details
Tip: Click on the bar to expand more detailed information
Test #1:
score: 100
Accepted
time: 1ms
memory: 3564kb
input:
5 3 45 10 20 30 0 0 + 200 2 5 + 10 20 40 - 100 21 16 + 10 50 0 + 22
output:
20 20 10 7 30 30 10 60 10 105
result:
ok 10 numbers
Test #2:
score: 0
Accepted
time: 1ms
memory: 3536kb
input:
1 1 1 0 0 0 - 1
output:
0 0
result:
ok 2 number(s): "0 0"
Test #3:
score: 0
Accepted
time: 1ms
memory: 3696kb
input:
5 3 33 3 24 23 12 24 - 9 16 28 - 1 17 27 - 9 19 26 - 5 32 22 - 2
output:
24 12 23 21 3 41 24 21 3 51
result:
ok 10 numbers
Test #4:
score: 0
Accepted
time: 1ms
memory: 3480kb
input:
4 5 6 1 3 4 2 0 2 1 + 2 7 3 + 6 9 0 + 9 10 1 - 6
output:
1 2 3 7 0 9 1 10
result:
ok 8 numbers
Test #5:
score: -100
Wrong Answer
time: 2ms
memory: 3828kb
input:
736 30 100500 99382 85511 67593 53450 55531 9959 37170 57546 52666 62342 50707 71285 65933 19874 2092 100255 23965 83091 45652 64171 100128 19518 21445 96069 79781 52642 37943 95321 97569 69154 0 44619 + 7052 2 72499 + 29247 3 53785 - 35614 5 81887 + 64475 7 8561 + 31641 8 95471 - 22654 9 61040 - 44...
output:
53450 310331 95321 22824 53450 338 67593 186711 99382 593328 95321 158 83091 580958 62342 71243 95321 759206 83091 183 2092 375130 99382 756951 100128 641870 64171 5285 50707 288492 96069 846290 2092 284 100255 605687 53450 615009 52642 683384 69154 5302 83091 155808 57546 351069 2092 231938 79781 7...
result:
wrong answer 9th numbers differ - expected: '23965', found: '99382'