結果
| 問題 |
No.3025 Chocol∀te
|
| コンテスト | |
| ユーザー |
👑 potato167
|
| 提出日時 | 2025-04-17 09:48:17 |
| 言語 | C++17 (gcc 13.3.0 + boost 1.87.0) |
| 結果 |
AC
|
| 実行時間 | 843 ms / 2,000 ms |
| コード長 | 4,174 bytes |
| コンパイル時間 | 2,413 ms |
| コンパイル使用メモリ | 213,308 KB |
| 実行使用メモリ | 39,352 KB |
| 最終ジャッジ日時 | 2025-04-17 09:48:59 |
| 合計ジャッジ時間 | 29,495 ms |
|
ジャッジサーバーID (参考情報) |
judge1 / judge5 |
(要ログイン)
| ファイルパターン | 結果 |
|---|---|
| sample | AC * 1 |
| other | AC * 77 |
ソースコード
#include <bits/stdc++.h>
using namespace std;
using ll = long long;
const int MAXN = 100000;
const int B = 450; // threshold for heavy
int main() {
ios::sync_with_stdio(false);
cin.tie(nullptr);
int N, M;
cin >> N >> M;
vector<unordered_set<int>> adj(N + 1);
vector<int> deg(N + 1, 0);
for (int i = 0; i < M; i++) {
int x, y;
cin >> x >> y;
adj[x].insert(y);
adj[y].insert(x);
deg[x]++;
deg[y]++;
}
vector<ll> A(N + 1);
for (int i = 1; i <= N; i++) {
cin >> A[i];
}
// heavy‐light initialization
vector<bool> isHeavy(N + 1, false);
vector<int> heavyIndex(N + 1, -1);
vector<int> heavyNodes;
vector<ll> heavySum;
vector< bitset<MAXN+1> > heavyBitsets;
// classify initial heavies
for (int i = 1; i <= N; i++) {
if (deg[i] > B) {
heavyIndex[i] = heavyNodes.size();
heavyNodes.push_back(i);
isHeavy[i] = true;
heavySum.push_back(0);
heavyBitsets.emplace_back();
}
}
// build heavy data
for (int h = 0; h < (int)heavyNodes.size(); h++) {
int u = heavyNodes[h];
auto &bs = heavyBitsets[h];
bs.reset();
ll s = 0;
for (int v : adj[u]) {
bs.set(v);
s += A[v];
}
heavySum[h] = s;
}
int Q;
cin >> Q;
while (Q--) {
int t;
cin >> t;
if (t == 1) {
int u, v;
cin >> u >> v;
bool added = false;
if (adj[u].count(v)) {
// remove edge
adj[u].erase(v);
adj[v].erase(u);
deg[u]--; deg[v]--;
} else {
// add edge
adj[u].insert(v);
adj[v].insert(u);
deg[u]++; deg[v]++;
added = true;
}
// update existing heavies for u/v
if (isHeavy[u]) {
int h = heavyIndex[u];
if (added) {
heavyBitsets[h].set(v);
heavySum[h] += A[v];
} else {
heavyBitsets[h].reset(v);
heavySum[h] -= A[v];
}
}
if (isHeavy[v]) {
int h = heavyIndex[v];
if (added) {
heavyBitsets[h].set(u);
heavySum[h] += A[u];
} else {
heavyBitsets[h].reset(u);
heavySum[h] -= A[u];
}
}
// dynamic classify newly heavy nodes
for (int x : {u, v}) {
if (!isHeavy[x] && deg[x] > B) {
// become heavy
int h = heavyNodes.size();
isHeavy[x] = true;
heavyIndex[x] = h;
heavyNodes.push_back(x);
heavySum.push_back(0);
heavyBitsets.emplace_back();
auto &bs2 = heavyBitsets[h];
bs2.reset();
ll s2 = 0;
for (int w : adj[x]) {
bs2.set(w);
s2 += A[w];
}
heavySum[h] = s2;
}
}
}
else if (t == 2) {
int p;
ll a;
cin >> p >> a;
ll delta = a - A[p];
A[p] = a;
// update sums of all heavies that are adjacent to p
for (int h = 0; h < (int)heavyNodes.size(); h++) {
if (heavyBitsets[h].test(p)) {
heavySum[h] += delta;
}
}
}
else if (t == 3) {
int c;
cin >> c;
if (isHeavy[c]) {
cout << heavySum[heavyIndex[c]] << "\n";
} else {
ll s = 0;
for (int v : adj[c]) {
s += A[v];
}
cout << s << "\n";
}
}
}
return 0;
}
potato167