QOJ.ac
QOJ
ID | 题目 | 提交者 | 结果 | 用时 | 内存 | 语言 | 文件大小 | 提交时间 | 测评时间 |
---|---|---|---|---|---|---|---|---|---|
#862893 | #9732. Gathering Mushrooms | Zawos | WA | 51ms | 5860kb | C++20 | 7.0kb | 2025-01-19 10:41:55 | 2025-01-19 10:41:56 |
Judging History
answer
#include <bits/stdc++.h>
#include <ext/pb_ds/assoc_container.hpp>
#include <ext/pb_ds/tree_policy.hpp>
#define FOR(i,a,b) for (int i = (a); i < (b); i++)
using namespace std;
using namespace __gnu_pbds;
using ll=long long;
using ld=long double;
using vi=vector<int>;
template<class T> using oset =tree<T, null_type, less<T>, rb_tree_tag,tree_order_statistics_node_update> ;
//上
const int N = 200005;
const ll inf = 1000000000000000000;
int par[N][20];
int par1[N][20];
ll k;
map<ll,ll>mp;
void init_par(vector<int> &parent){
int n = parent.size();
for(int i = 0; i < n;i++){
if(parent[i] == -1) par[i][0] = i;
else par[i][0] = parent[i];
}
for(int i = 1; i < 20; i++){
for(int j = 0; j < n; j++) par[j][i] = par[par[j][i-1]][i-1];
}
}
void init_par2(vector<int> &parent){
int n = parent.size();
for(int i = 0; i < n;i++){
par1[i][0] = parent[i];
}
for(int i = 1; i < 20; i++){
for(int j = 0; j < n; j++) if(parent[j] != -1) par1[j][i] = par1[par1[j][i-1]][i-1];
}
}
ll jump(int x,int y){
ll su = 1;
for(int i = 19; i>= 0;i--){
if(par[x][i] != y&&par[x][y] != x) x = par[x][i],su +=(1<<i);
}
return su;
}
int move(int x,ll dis){
for(int i = 0; i < 20 ; i++){
if(dis&(1<<i)) x = par[x][i];
}
return x;
}
int move2(int x,ll dis){
for(int i = 0; i < 20 ; i++){
if(dis&(1<<i)) x = par1[x][i];
}
return x;
}
void toposort(int x,vector<vector<int>> &AL,vector<int>&vis,vector<int> &topo){
vis[x] = 1;
for(auto &u: AL[x]){
if(vis[u] == 0) toposort(u,AL,vis,topo);
}
topo.push_back(x);
}
void dfs(int x,int c,vector<vector<int>> &AL,vector<int> &scc){
scc[x] = c;
for(auto &u: AL[x]){
if(scc[u] == -1) dfs(u,c,AL,scc);
}
}
void create_ancester_tree(int x,int root,vector<int> &v,vector<vector<int>> &nAL,vector<int> & parent,vector<int> &last,vector<int>&depth){
if(x != root){
if(last[v[x]] != -1) parent[x] = last[v[x]];
else parent[x] = root;
last[v[x]] = x;
}
for(auto &u: nAL[x]){
depth[u] = depth[x] + 1;
create_ancester_tree(u,root,v,nAL,parent,last,depth);
}
if(x!=root) last[v[x]] = parent[x];
}
vector<ll> calc_cycle(int x,vector<vector<int>> &AL,vector<int> &v,vector<ll> &ans,vector<ll> &distance,vector<int>&position,vector<int>&last,vector<int>&parent){
ll sz = 1;
int p1 = x;
int p2 = x;
map<int,ll> val;
ll mx = 1;
val[v[x]]++;
position[p1] = sz-1;
last[v[p1]] = -1;
vector<ll> cyc = {x};
while(AL[p1][0] != x){
p1 =AL[p1][0],sz++;
position[p1] = sz-1;
last[v[p1]] = -1;
cyc.push_back(p1);
mx = max(mx,++val[v[p1]]);
}
ll vueltas = ((k+mx-1)/mx-1);
for(auto &u:val){
u.second = u.second*vueltas;
}
p1 = x;
ll d = 0;
val[v[p1]]++;
for(int i = 0; i < sz;i++){
while(true){
if(val[v[p2]] == k){
distance[p1] = vueltas*sz+d;
ans[p1] = v[p2];
break;
}else{
p2 = AL[p2][0];
val[v[p2]]++;
d++;
}
}
d--;
val[v[p1]]--;
p1 = AL[p1][0];
}
p1 = x;
for(int i = 0; i <2*sz;i++){
if(last[v[p1]] != -1){
parent[last[v[p1]]] = p1;
}
last[v[p1]] = p1;
p1 = AL[p1][0];
}
return cyc;
}
void calc_tree(int x,int root,ll sz,vector<vector<int>> &AL,vector<int> &v,vector<ll> & ans,vector<ll> &distance,vector<int> &last,vector<int>&depth,vector<int>&position){
for(auto &u: AL[x]){
ll steps = 0;
ll su = 0;
ll toroot = jump(u,root);
if(toroot >= k){
su = depth[u]-depth[move(u,k-1)];
}else{
if(last[v[u]] !=-1){
steps = toroot;
su = depth[u];
if(position[last[v[u]]] >= position[root]){
su +=position[last[v[u]]] -position[root];
}else{
su += sz-position[root]+position[last[v[u]]];
}
ll many = mp[v[u]];
ll o = (k-steps +many-1)/many-1;
steps += o* many;
su+=o*sz;
ll extra =move2(position[last[v[u]]],k-steps-1);
if(extra >= position[last[v[u]]]){
su += extra-position[last[v[u]]];
}else su += sz-position[last[v[u]]]+extra;
}else su = inf;
}
if(su <distance[x] +1){
distance[u] = su;
ans[u] = v[u];
}else{
distance[u] = distance[x]+1;
ans[u] = ans[x];
}
calc_tree(u,root,sz,AL,v,ans,distance,last,depth,position);
}
}
int main(){
ios_base::sync_with_stdio(false);
cin.tie(NULL);
// freopen("18.01.2025\\input.txt","r",stdin);
// freopen("18.01.2025\\output.txt","w",stdout);
int t;
cin >> t;
while(t--){
ll n; cin >> n >> k;
vector<vector<int>> AL(n),AL_T(n);
vector<int> v(n),scc(n,-1),vis(n),parent(n,-1),last(n,-1),depth(n),position(n),aux(n,-1);
vector<ll> ans(n,-1),distance(n);
vector<int>topo;
FOR(i,0,n){cin >> v[i];v[i]--;}
FOR(i,0,n){
int x; cin >> x;
x--; AL[i].push_back(x); AL_T[x].push_back(i);
}
for(int i = 0; i < n; i++){
if(!vis[i]) toposort(i,AL,vis,topo);
}
reverse(topo.begin(),topo.end());
int cur = 0;
for(auto &u: topo){
if(scc[u] == -1) dfs(u,cur++,AL_T,scc);
}
vector<vector<int>> nAL(n);
for(int i = 0; i < n; i++){
if(scc[AL[i][0]] != scc[i]) nAL[AL[i][0]].push_back(i);
}
for(int i = 0; i < n; i++){
if(scc[AL[i][0]] == scc[i]) create_ancester_tree(i,i,v,nAL,parent,last,depth);
}
init_par(parent);
for(int i = 0; i < n; i++) parent[i] = -1;
vector<vector<ll>> temp;
for(int i = 0; i < n; i++){
if(scc[AL[i][0]] == scc[i] && ans[i] == -1){
temp.push_back(calc_cycle(i,AL,v,ans,distance,position,last,parent));
}
}
init_par2(parent);
for(int i = 0; i < n; i++) last[i] = -1;
for(auto &u: temp){
mp.clear();
for(int i = (int)u.size()-1; i >= 0;i--){
last[v[u[i]]] = u[i];
mp[v[u[i]]]++;
}
for(int i = (int)u.size()-1; i >= 0;i--){
calc_tree(u[i],u[i],u.size(),nAL,v,ans,distance,last,depth,position);
last[v[u[i]]] = u[i];
}
for(int i = 0; i < u.size();i++) last[v[u[i]]] = -1;
}
ll re = 0;
for(ll i = 1; i <= n;i++) re += i*(ans[i-1]+1);
cout <<re<<'\n';
}
}
详细
Test #1:
score: 100
Accepted
time: 0ms
memory: 5860kb
input:
3 5 3 2 2 1 3 3 2 5 1 2 4 5 4 2 2 1 3 3 2 5 1 2 4 3 10 1 2 3 1 3 2
output:
41 45 14
result:
ok 3 lines
Test #2:
score: -100
Wrong Answer
time: 51ms
memory: 5692kb
input:
6000 19 48 18 19 18 19 11 9 15 19 12 18 11 18 9 18 9 18 19 11 15 12 14 18 8 1 3 19 5 13 14 15 2 14 5 19 2 19 12 9 15 23 3 1 1 3 6 1 4 1 1 6 6 4 12 4 6 14 1 8 8 6 6 12 14 6 8 5 7 14 2 5 9 140979583 4 5 8 9 2 7 6 8 2 8 9 4 6 9 2 4 7 8 4 976357580 2 3 1 3 2 1 1 4 6 508962809 4 3 4 3 4 4 4 5 4 5 5 6 13 ...
output:
2601 260 254 26 84 743 126 30 1092 1 2367 2422 168 360 338 324 2424 2520 220 228 1104 9 3486 1 796 81 340 272 600 2566 32 495 40 128 140 665 1502 702 68 96 90 288 29 561 16 234 445 3114 140 40 477 1237 19 1994 1082 32 613 672 20 390 32 2204 1942 42 21 885 4 855 196 420 11 1408 793 720 1 556 40 17 21...
result:
wrong answer 1st lines differ - expected: '3420', found: '2601'