답안 #598755

# 제출 시각 아이디 문제 언어 결과 실행 시간 메모리
598755 2022-07-18T23:20:00 Z Bobaa Training (IOI07_training) C++17
100 / 100
43 ms 24552 KB
#include<bits/stdc++.h>
#define st first
#define nd second
using namespace std;
using pii = pair<int, int>;
const int K=10, N=1<<K;
vector<int> E[N], lca[N];
int id[N], d[N], par[N], pre[N], post[N];
int wsk;
int dp[N][1<<K];
int dp2[N][5*N];
int n, m;
vector<pair<int, pii > > edg, edg2;
vector<int> dob;
void dfs(int v, int p){
	pre[v]=wsk++;
	par[v]=p;
	d[v]=d[p]+1;
	for(int i=0; i<E[v].size(); i++)if(E[v][i]==p)swap(E[v][i], E[v].back());
	if(p!=0)E[v].pop_back();
	for(int i=0; i<E[v].size(); i++){
		id[E[v][i]]=i;
		dfs(E[v][i], v);
	}
	post[v]=wsk;
}
void dfs2(int v){
	for(int u:E[v]){
		dfs2(u);
		dp[v][1<<id[u]]=dp2[u][0];
	}
	for(int e:lca[v]){
		int u=edg[e].nd.st, w=edg[e].nd.nd;
		while(par[w]!=v)w=par[w];
		if(u==v){
			dp[v][1<<id[w]]=max(edg[e].st + dp2[w][e], dp[v][1<<id[w]]);
		}
		else{
			while(par[u]!=v)u=par[u];
			dp[v][(1<<id[u])+(1<<id[w])]=max(edg[e].st+dp2[u][e]+dp2[w][e], dp[v][(1<<id[u])+(1<<id[w])]);
		}
	}
	for(int i=0; i<(1<<E[v].size()); i++){
		for(int j=i; ; j=(j-1)&i){
			dp[v][i]=max(dp[v][i], dp[v][j]+dp[v][i-j]);
			if(j==0)break;
		}
	}
	for(int e:dob){
		if(edg[e].nd.st==v && pre[edg[e].nd.nd]>=post[v]){
			dp2[v][e]=dp[v][(1<<E[v].size())-1];
		}
		if(edg[e].nd.nd==v){
			dp2[v][e]=dp[v][(1<<E[v].size())-1];
		}
		if(par[edg2[e].nd.st]==v ^ par[edg2[e].nd.nd]==v){
			if(par[edg2[e].nd.st]==v){
				dp2[v][e]=dp[v][(1<<E[v].size())-1-(1<<id[edg2[e].nd.st])]+dp2[edg2[e].nd.st][e];
				edg2[e].nd.st=v;
			}
			if(par[edg2[e].nd.nd]==v){
				dp2[v][e]=dp[v][(1<<E[v].size())-1-(1<<id[edg2[e].nd.nd])]+dp2[edg2[e].nd.nd][e];
				edg2[e].nd.nd=v;
			}
		}
	}
	dp2[v][0]=dp[v][(1<<E[v].size())-1];
}
int main(){
	ios_base::sync_with_stdio(false); 
	cin.tie(nullptr); 
	cin>>n>>m;
	int sum=0;
	for(int i=0; i<m; i++){
		int u, v, w;
		cin>>u>>v>>w;
		sum+=w;
		edg.push_back({w, {u, v}});
		if(w==0){
			E[u].push_back(v);
			E[v].push_back(u);
		}
	}
	dfs(1, 0);
	sort(edg.begin(), edg.end());
	for(int i=n-1; i<m; i++){
		if(pre[edg[i].nd.st]>pre[edg[i].nd.nd])swap(edg[i].nd.st, edg[i].nd.nd);
		int u=edg[i].nd.st, v=edg[i].nd.nd;
		if((d[u]&1)!=(d[v]&1)){
			continue;
		}
		if(d[u]<d[v])swap(u, v);
		while(d[u]>d[v]){
			u=par[u];
		}
		while(u!=v){
			u=par[u];
			v=par[v];
		}
		dob.push_back(i);
		lca[u].push_back(i);
	}
	edg2=edg;
	dfs2(1);
	cout<<sum-dp2[1][0];
}

Compilation message

training.cpp: In function 'void dfs(int, int)':
training.cpp:19:16: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<int>::size_type' {aka 'long unsigned int'} [-Wsign-compare]
   19 |  for(int i=0; i<E[v].size(); i++)if(E[v][i]==p)swap(E[v][i], E[v].back());
      |               ~^~~~~~~~~~~~
training.cpp:21:16: warning: comparison of integer expressions of different signedness: 'int' and 'std::vector<int>::size_type' {aka 'long unsigned int'} [-Wsign-compare]
   21 |  for(int i=0; i<E[v].size(); i++){
      |               ~^~~~~~~~~~~~
training.cpp: In function 'void dfs2(int)':
training.cpp:56:24: warning: suggest parentheses around comparison in operand of '^' [-Wparentheses]
   56 |   if(par[edg2[e].nd.st]==v ^ par[edg2[e].nd.nd]==v){
      |      ~~~~~~~~~~~~~~~~~~^~~
# 결과 실행 시간 메모리 Grader output
1 Correct 0 ms 468 KB Output is correct
2 Correct 1 ms 468 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 1 ms 724 KB Output is correct
2 Correct 1 ms 724 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 20 ms 20564 KB Output is correct
2 Correct 17 ms 20640 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 0 ms 468 KB Output is correct
2 Correct 1 ms 468 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 1 ms 596 KB Output is correct
2 Correct 1 ms 632 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 1 ms 1108 KB Output is correct
2 Correct 1 ms 1108 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 4 ms 3712 KB Output is correct
2 Correct 3 ms 3924 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 8 ms 8480 KB Output is correct
2 Correct 8 ms 8360 KB Output is correct
3 Correct 7 ms 8148 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 22 ms 21844 KB Output is correct
2 Correct 21 ms 22400 KB Output is correct
3 Correct 22 ms 23272 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 7 ms 7380 KB Output is correct
2 Correct 11 ms 8452 KB Output is correct
3 Correct 43 ms 24552 KB Output is correct
4 Correct 10 ms 8532 KB Output is correct
# 결과 실행 시간 메모리 Grader output
1 Correct 24 ms 15764 KB Output is correct
2 Correct 34 ms 17004 KB Output is correct
3 Correct 26 ms 21460 KB Output is correct
4 Correct 23 ms 23200 KB Output is correct