제출 #1345859

#제출 시각아이디문제언어결과실행 시간메모리
1345859PieArmyWild Boar (JOI18_wild_boar)C++20
100 / 100
2100 ms300604 KiB
#include<bits/stdc++.h>
typedef long long ll;
#define pb push_back
#define fr first
#define sc second
#define endl '\n'
using namespace std;
#define mid ((left+right)>>1)
const ll inf=1e18;
const int k=4;
struct path{
	int a=0,b=0;
	ll c=inf;
	path(){}
	path(int a,int b,ll c):a(a),b(b),c(c){}
};
bool operator<(path a,path b){
	return a.c<b.c;
}
bool operator>(path a,path b){
	return a.c>b.c;
}
bool operator<=(path a,path b){
	return a.c<=b.c;
}
bool operator>=(path a,path b){
	return a.c>=b.c;
}
bool operator==(path a,path b){
	return a.c==b.c;
}
bool operator!=(path a,path b){
	return a.c!=b.c;
}
typedef array<path,k> ar;

bool f(ar arr){
	int n=0;
	while(n<k&&arr[n].c!=inf)n++;
	for(int i=0;i<n;i++){
		for(int j=i+1;j<n;j++){
			if(arr[i].a==arr[j].a&&arr[i].b==arr[j].b)return false;
		}
	}
	if(n>=3){
		int cnta=0,cntb=0;
		for(int i=1;i<n;i++){
			if(arr[i].a==arr[0].a)cnta++;
			if(arr[i].b==arr[0].b)cntb++;
		}
		if(cnta>=2||cntb>=2)return false;
	}
	if(n==4){
		for(int i=0;i<n;i++){
			int cnt=0;
			int sec=0;
			for(int j=0;j<n;j++){
				if(i==j)continue;
				if(arr[j].a==arr[i].a){
					cnt++;
					continue;
				}
				if(sec==0){
					sec=arr[j].b;
					cnt++;
					continue;
				}
				if(sec==arr[j].b){
					cnt++;
				}
			}
			if(cnt==3)return false;
		}
	}
	return true;
}

struct Seg{
	int n;
	vector<ar>tree;
	ar comb(ar x,ar y){
		ar res;
		vector<path>v;
		for(int i=0;i<k;i++){
			for(int j=0;j<k;j++){
				if(x[i].c==inf||y[j].c==inf)continue;
				if(x[i].b==y[j].a)continue;
				v.pb(path(x[i].a,y[j].b,x[i].c+y[j].c));
			}
		}
		sort(v.begin(),v.end());
		int p=0;
		for(auto x:v){
			res[p]=x;
			if(f(res)){
				p++;
				if(p==k)break;
			}
			res[p]=path();
		}
		return res;
	}
	void init(int N){
		n=N;
		tree.resize(n<<2);
	}
	int t;
	ar x;
	void up(int node=1,int left=1,int right=-1){
		if(right==-1)right=n;
		if(left==right){
			tree[node]=x;
			return;
		}
		if(t>mid)up(node*2+1,mid+1,right);
		else up(node*2,left,mid);
		tree[node]=comb(tree[node*2],tree[node*2+1]);
	}
	void update(int tar,ar val){
		t=tar;x=val;
		up();
	}
};

int n,m,l,t;
vector<pair<int,int>>komsu[2023];
int arr[100023];
pair<int,int>upd[100023];
ar table[2023][2023];
vector<path>can[2023];
int vis[2023];
Seg seg;

signed main(){
	ios_base::sync_with_stdio(23^23);cin.tie(0);
	cin>>n>>m>>t>>l;
	for(int i=1;i<=m;i++){
		int x,y,z;cin>>x>>y>>z;
		komsu[x].pb({y,z});
		komsu[y].pb({x,z});
	}
	for(int i=1;i<=l;i++){
		cin>>arr[i];
	}
	for(int i=1;i<=t;i++){
		cin>>upd[i].fr>>upd[i].sc;
	}
	for(int i=1;i<=n;i++){
		priority_queue<pair<ll,pair<int,int>>,vector<pair<ll,pair<int,int>>>,greater<pair<ll,pair<int,int>>>>pq;
		for(int j=1;j<=n;j++){
			can[j].clear();
		}
		for(auto[root,o]:komsu[i]){
			for(int j=1;j<=n;j++){
				vis[j]=0;
			}
			pq.push({o,{root,i}});
			while(pq.size()){
				ll cost=pq.top().fr;
				int pos=pq.top().sc.fr;
				int las=pq.top().sc.sc;
				pq.pop();
				if(vis[pos]==-1)continue;
				if(pos!=i)can[pos].pb(path(root,las,cost));
				if(vis[pos]){
					for(auto x:komsu[pos]){
						if(vis[x.fr]==-1)continue;
						if(x.fr==vis[pos]){
							pq.push({cost+x.sc,{x.fr,pos}});
						}
					}
					vis[pos]=-1;
				}
				else{
					vis[pos]=las;
					for(auto x:komsu[pos]){
						if(x.fr==las)continue;
						if(vis[x.fr]==pos)continue;
						if(vis[x.fr]==-1)continue;
						pq.push({cost+x.sc,{x.fr,pos}});
					}
				}
			}
		}
		for(int j=1;j<=n;j++){
			sort(can[j].begin(),can[j].end());
			int p=0;
			for(auto x:can[j]){
				table[i][j][p]=x;
				if(f(table[i][j])){
					p++;
					if(p==k)break;
				}
				table[i][j][p]=path();
			}
		}
	}
	seg.init(l-1);
	for(int i=1;i<l;i++){
		seg.update(i,table[arr[i]][arr[i+1]]);
	}
	for(int i=1;i<=t;i++){
		arr[upd[i].fr]=upd[i].sc;
		if(upd[i].fr!=1){
			seg.update(upd[i].fr-1,table[arr[upd[i].fr-1]][arr[upd[i].fr]]);
		}
		if(upd[i].fr!=l){
			seg.update(upd[i].fr,table[arr[upd[i].fr]][arr[upd[i].fr+1]]);
		}
		ll cev=seg.tree[1][0].c;
		/*if(true){
			for(int i=1;i<l;i++){
				cerr<<arr[i]<<"   ";
				for(int j=0;j<k;j++){
					cerr<<table[arr[i]][arr[i+1]][j].c<<":"<<table[arr[i]][arr[i+1]][j].a<<"-"<<table[arr[i]][arr[i+1]][j].b<<" | ";
				}
				cerr<<endl;
			}
			cerr<<arr[l]<<endl;
			cerr<<endl;
			for(int j=0;j<k;j++){
				cerr<<seg.tree[3][j].c
				<<":"<<seg.tree[3][j].a
				<<"-"<<seg.tree[3][j].b<<" | ";
			}
			cerr<<endl;
			for(int j=0;j<k;j++){
				cerr<<seg.tree[6][j].c
				<<":"<<seg.tree[6][j].a
				<<"-"<<seg.tree[6][j].b<<" | ";
			}
			cerr<<endl;
			for(int j=0;j<k;j++){
				cerr<<seg.tree[7][j].c
				<<":"<<seg.tree[7][j].a
				<<"-"<<seg.tree[7][j].b<<" | ";
			}
			cerr<<endl;
			cerr<<cev<<endl;
			return 0;
		}*/
		if(cev>=inf)cev=-1;
		cout<<cev<<endl;
	}
}
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...