题意:

n<=1e5,1<=a[i][j]<=1e9

思路:

不是很懂INF为什么要开到1e15,我觉得只要1e14就好

 #include<bits/stdc++.h>
using namespace std;
typedef long long ll;
typedef unsigned int uint;
typedef unsigned long long ull;
typedef pair<int,int> PII;
typedef pair<ll,ll> Pll;
typedef vector<int> VI;
typedef vector<PII> VII;
//typedef pair<ll,ll>P;
#define N 200010
#define M 200010
#define fi first
#define se second
#define MP make_pair
#define pb push_back
#define pi acos(-1)
#define mem(a,b) memset(a,b,sizeof(a))
#define rep(i,a,b) for(int i=(int)a;i<=(int)b;i++)
#define per(i,a,b) for(int i=(int)a;i>=(int)b;i--)
#define lowbit(x) x&(-x)
#define Rand (rand()*(1<<16)+rand())
#define id(x) ((x)<=B?(x):m-n/(x)+1)
#define ls p<<1
#define rs p<<1|1 struct node
{
int x,y;
}pre[N][][]; ll dp[N][][];
ll a[N][];
int head[N],vet[N],nxt[N],d[N],c[N],son[N],f[N],tot,n; int read()
{
int v=,f=;
char c=getchar();
while(c<||<c) {if(c=='-') f=-; c=getchar();}
while(<=c&&c<=) v=(v<<)+v+v+c-,c=getchar();
return v*f;
} void add(int a,int b)
{
nxt[++tot]=head[a];
vet[tot]=b;
head[a]=tot;
} void dfs(int u,int fa)
{
//printf("dfs u=%d fa=%d\n",u,fa);
int e=head[u],s=;
rep(i,,)
rep(j,,) dp[u][i][j]=1e15;
while(e)
{
int v=vet[e];
if(v!=fa)
{
s++;
son[u]=v;
f[v]=u;
dfs(v,u);
}
e=nxt[e];
}
if(u==&&d[]==)
{
//printf("case 2\n");
return;
} if(s==)
{
rep(i,,)
rep(j,,)
if(i!=j) dp[u][i][j]=a[u][i];
}
else
{
int v=son[u];
//printf("u=%d v=%d\n",u,v);
rep(i,,)
rep(j,,)
rep(k,,)
if(i!=j&&j!=k&&i!=k)
{
if(dp[u][i][j]>dp[v][j][k]+a[u][i])
{
dp[u][i][j]=dp[v][j][k]+a[u][i];
pre[u][i][j].x=j;
pre[u][i][j].y=k;
}
} } } void print()
{
/*rep(i,1,n)
rep(j,0,2)
rep(k,0,2)
if(j!=k) printf("i=%d j=%d k=%d dp[i][j][k]=%I64d\n",i,j,k,dp[i][j][k]);*/
if(d[]==)
{
ll ans=1e15;
int x=,y=;
rep(i,,)
rep(j,,)
if(i!=j&&dp[][i][j]<ans)
{
ans=dp[][i][j];
x=i; y=j;
}
int u=;
while(u)
{
c[u]=x;
int x1=pre[u][x][y].x;
int y1=pre[u][x][y].y;
u=son[u];
x=x1,y=y1;
}
printf("%I64d\n",ans);
rep(i,,n) printf("%d ",c[i]+);
}
else
{
int k1=,k2=;
rep(i,,n)
if(f[i]==){k1=i; break;}
per(i,n,)
if(f[i]==){k2=i; break;}
int x1,y1,x2,y2,z;
ll ans=1e15;
rep(i,,)
rep(j,,)
rep(k,,)
rep(p,,)
rep(q,,)
if(i!=j&&i!=k&&j!=k&&j!=p&&p!=i&&i!=q&&k!=q&&dp[k1][j][p]+dp[k2][k][q]+a[][i]<ans)
{
ans=dp[k1][j][p]+dp[k2][k][q]+a[][i];
z=i;
x1=j; y1=p;
x2=k; y2=q;
}
c[]=z;
int u=k1,x=x1,y=y1;
while(u)
{
c[u]=x;
int x1=pre[u][x][y].x;
int y1=pre[u][x][y].y;
u=son[u];
x=x1,y=y1;
}
u=k2,x=x2,y=y2;
while(u)
{
c[u]=x;
int x1=pre[u][x][y].x;
int y1=pre[u][x][y].y;
u=son[u];
x=x1,y=y1;
}
printf("%I64d\n",ans);
rep(i,,n) printf("%d ",c[i]+);
} } int main()
{
//freopen("1.in","r",stdin);
n=read();
rep(j,,)
rep(i,,n) scanf("%I64d",&a[i][j]);
rep(i,,n) head[i]=d[i]=;
tot=;
rep(i,,n-)
{
int x=read(),y=read();
add(x,y);
add(y,x);
d[x]++; d[y]++;
}
int flag=;
rep(i,,n)
if(d[i]>=) flag=;
if(!flag)
{
printf("-1\n");
return ;
}
dfs(,);
print();
return ;
}

实际上只有1条或者2条从1下来的链,枚举1和与1相邻的颜色然后就能推出整条链

 #include<bits/stdc++.h>
using namespace std;
typedef long long ll;
typedef unsigned int uint;
typedef unsigned long long ull;
typedef pair<int,int> PII;
typedef pair<ll,ll> Pll;
typedef vector<int> VI;
typedef vector<PII> VII;
//typedef pair<ll,ll>P;
#define N 200010
#define M 200010
#define fi first
#define se second
#define MP make_pair
#define pb push_back
#define pi acos(-1)
#define mem(a,b) memset(a,b,sizeof(a))
#define rep(i,a,b) for(int i=(int)a;i<=(int)b;i++)
#define per(i,a,b) for(int i=(int)a;i>=(int)b;i--)
#define lowbit(x) x&(-x)
#define Rand (rand()*(1<<16)+rand())
#define id(x) ((x)<=B?(x):m-n/(x)+1)
#define ls p<<1
#define rs p<<1|1 const ll MOD=1e9+,inv2=(MOD+)/;
double eps=1e-;
ll INF=1e15;
int da[]={-,,,};
int db[]={,,-,}; struct node
{
int x,y;
}pre[N][][]; ll a[N][];
int head[N],vet[N],nxt[N],f[N],g[N],b[N],c[N],d[N],p[N],tot,son; int read()
{
int v=,f=;
char c=getchar();
while(c<||<c) {if(c=='-') f=-; c=getchar();}
while(<=c&&c<=) v=(v<<)+v+v+c-,c=getchar();
return v*f;
} void add(int a,int b)
{
nxt[++tot]=head[a];
vet[tot]=b;
head[a]=tot;
} void dfs(int u,int fa)
{
int e=head[u];
while(e)
{
int v=vet[e];
if(v!=fa)
{
f[v]=u;
g[u]=v;
if(u==)
{
son++;
p[son]=v;
}
dfs(v,u);
}
e=nxt[e];
}
} int main()
{
//freopen("1.in","r",stdin);
int n=read();
rep(j,,)
rep(i,,n) scanf("%I64d",&a[i][j]);
rep(i,,n) head[i]=d[i]=;
tot=;
rep(i,,n-)
{
int x=read(),y=read();
add(x,y);
add(y,x);
d[x]++; d[y]++;
}
int flag=;
rep(i,,n)
if(d[i]>=) flag=;
if(!flag)
{
printf("-1\n");
return ;
}
son=;
dfs(,);
ll ans=INF;
if(son==)
{
rep(x,,)
{
int u=p[];
rep(y,,)
if(x!=y)
{
b[]=x; b[u]=y;
int k=u;
while(k)
{
k=g[k];
if(!k) break;
b[k]=-b[f[k]]-b[f[f[k]]];
}
ll s=;
rep(i,,n) s+=a[i][b[i]];
if(s<ans)
{
ans=s;
rep(i,,n) c[i]=b[i];
}
}
}
}
else
{
int u1=p[],u2=p[];
rep(x,,)
rep(y,,)
rep(z,,)
if(x!=y&&x!=z&&y!=z)
{
b[]=x; b[u1]=y;
int k=u1;
while(k)
{
k=g[k];
if(!k) break;
b[k]=-b[f[k]]-b[f[f[k]]];
}
b[u2]=z;
k=u2;
while(k)
{
k=g[k];
if(!k) break;
b[k]=-b[f[k]]-b[f[f[k]]];
}
ll s=;
rep(i,,n) s+=a[i][b[i]];
if(s<ans)
{
ans=s;
rep(i,,n) c[i]=b[i];
}
}
} printf("%I64d\n",ans);
rep(i,,n) printf("%d ",c[i]+);
return ;
}

【CF1244D】Paint the Tree(树形DP,树)的更多相关文章

  1. E. Paint the Tree 树形dp

    E. Paint the Tree 题目大意:给你一棵树,每一个点都可以染k种颜色,你拥有无数种颜色,每一种颜色最多使用2次,如果一条边的两个节点拥有同一种颜色,那么就说 这条边是饱和的,一个树的价值 ...

  2. [HDU 5293]Tree chain problem(树形dp+树链剖分)

    [HDU 5293]Tree chain problem(树形dp+树链剖分) 题面 在一棵树中,给出若干条链和链的权值,求选取不相交的链使得权值和最大. 分析 考虑树形dp,dp[x]表示以x为子树 ...

  3. 树形DP+树状数组 HDU 5877 Weak Pair

    //树形DP+树状数组 HDU 5877 Weak Pair // 思路:用树状数组每次加k/a[i],每个节点ans+=Sum(a[i]) 表示每次加大于等于a[i]的值 // 这道题要离散化 #i ...

  4. 熟练剖分(tree) 树形DP

    熟练剖分(tree) 树形DP 题目描述 题目传送门 分析 我们设\(f[i][j]\)为以\(i\)为根节点的子树中最坏时间复杂度小于等于\(j\)的概率 设\(g[i][j]\)为当前扫到的以\( ...

  5. hdu6035 Colorful Tree 树形dp 给定一棵树,每个节点有一个颜色值。定义每条路径的值为经过的节点的不同颜色数。求所有路径的值和。

    /** 题目:hdu6035 Colorful Tree 链接:http://acm.hdu.edu.cn/showproblem.php?pid=6035 题意:给定一棵树,每个节点有一个颜色值.定 ...

  6. CF 461B Appleman and Tree 树形DP

    Appleman has a tree with n vertices. Some of the vertices (at least one) are colored black and other ...

  7. codeforces 161D Distance in Tree 树形dp

    题目链接: http://codeforces.com/contest/161/problem/D D. Distance in Tree time limit per test 3 secondsm ...

  8. POJ 1655.Balancing Act 树形dp 树的重心

    Balancing Act Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 14550   Accepted: 6173 De ...

  9. 5.10 省选模拟赛 tree 树形dp 逆元

    LINK:tree 整场比赛看起来最不可做 确是最简单的题目. 感觉很难写 不过单独考虑某个点 容易想到树形dp的状态. 设f[x]表示以x为根的子树内有黑边的方案数. 白边方案只有一种所以不用记录. ...

  10. hdu-5834 Magic boy Bi Luo with his excited tree(树形dp)

    题目链接: Magic boy Bi Luo with his excited tree Time Limit: 8000/4000 MS (Java/Others)    Memory Limit: ...

随机推荐

  1. Jenkins简介&邮箱配置

    一.Jenkins基本介绍: Jenkins是一个开源软件项目,是基于Java开发的一种持续集成工具,用于监控持续重复的工作,旨在提供一个开放易用的软件平台,使软件的持续集成变成可能.--摘自百科 二 ...

  2. value_counts()函数

    value_counts函数用于统计dataframe或series中不同数或字符串出现的次数 ascending=True时,按升序排列. normalize=True时,可计算出不同字符出现的频率 ...

  3. spring map获取同类型的bean

    今天看博客怎么减少if else 方法, 才发现spring 还有很多功能我没有用到,以后真的得花时间学学spring,今天学到的东西如下: 1.定义一个接口 store public interfa ...

  4. oracle linux 7使用udev绑盘操作

    参考:Oracle Linux 7: Udev rule for ASM Cannot Place the ASM Disk in a Directory under /dev (Doc ID 221 ...

  5. 使用 Spring HATEOAS 开发 REST 服务

    使用 Spring HATEOAS 开发 REST 服务 学习博客:https://www.ibm.com/developerworks/cn/java/j-lo-SpringHATEOAS/ htt ...

  6. python+selenium元素定位之CSS学习01

    参考文档:https://www.w3school.com.cn/cssref/css_selectors.asp 选择器 例子 例子描述 CSS .class .intro 选择 class=&qu ...

  7. [2019南京网络赛D题]Robots

    题目链接 2019.9.2更新 第二天睡醒想了想发现好像搜一遍就可以过,赛时写的花里胡哨的还错了,太菜了QAQ #include<bits/stdc++.h> using namespac ...

  8. 【摘】sizeof实现

    注意sizeof是运算符,而非函数 关于sizeof的两个精巧的宏实现. 非数组的sizeof: #defne _sizeof(T) ( (size_t)((T*)0 + 1)) 数组的sizeof: ...

  9. Elasticsearch7.X 入门学习第七课笔记-----Mapping多字段与自定义Analyzer

    原文:Elasticsearch7.X 入门学习第七课笔记-----Mapping多字段与自定义Analyzer 版权声明:本文为博主原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处 ...

  10. webpack打包发布项目

    1.打包 :npm run build 2.发布: 1)使用静态服务器工具包 npm install -g serve serve dist 访问:http://www.localhost.5000 ...