CF23 E. Tree 树形dp+高精度
题目链接
题解
CF竟让卡常QAQ
dp+高精度
dp[x][j]表示以x为根的子树,x所属的联通块大小为j,的最大乘积(不带j这块
最后f[x]维护以x为根的子树的最大答案
有点卡内存...高精压了4位
看了题解,了解到,其实这个dp的复杂度其实是O(n^2)
每次转移是复杂度是x之前的子树的sz * 当前子树的sz
相当于之前子树所有点和当前子树的点组成的点对数
而每个点对只会在lca处被计算一次
所以复杂度O(n^2)
代码
#include<cstdio>
#include<cstring>
#include<algorithm>
inline int read() {
int x = 0,f = 1;
char c = getchar();
while(c < '0' ||c > '9')c = getchar();
while(c <= '9' && c >= '0') x = x * 10 + c - '0',c = getchar();
return x * f;
}
const int L = 10000;
const int maxn = 701;
const int maxlen = 61;
struct Bignum{
int num[maxlen];
int len;
Bignum () {memset(num,0,sizeof num); len = 0; }
void print() {
for(int i = len;i;-- i)
if(i != len) {
if(num[i - 1] < L / 10) {
printf("0");
if(num[i - 1] < L / 100) {
printf("0");
if(num[i - 1] < L / 1000) printf("0");
}
}
printf("%d",num[i - 1]);
} else printf("%d",num[i - 1]);
puts("");
}
} dp[maxn][maxn],Max[maxn];
Bignum operator * (Bignum a,Bignum b) {
int len = 0;
Bignum ret;
for(int i = 0;i < a.len;i ++) for(int j = 0;j < b.len;j ++) {
ret.num[i + j] += a.num[i] * b.num[j];
if(ret.num[i + j] >= L) {
ret.num[i + j + 1] += ret.num[i + j] / L;
ret.num[i + j] %= L;
}
}
len = a.len + b.len;
while(ret.num[len-1] == 0 && len > 1) len --;
ret.len = len;
return ret;
}
Bignum operator / (Bignum a,int b) {
int len = a.len;
Bignum ret;
if(!b) return ret;
for(int i = 0;i < len;i ++) {
ret.num[i] += a.num[i]* b;
if(ret.num[i] >= L) {
ret.num[i+1] += ret.num[i] / L;
ret.num[i] %= L;
}
}
while(ret.num[len] > 0) ret.num[len+1] = ret.num[len] / L, ret.num[len ++] %= L;
ret.len = len;
return ret;
}
Bignum max(Bignum a,Bignum b) {
if(a.len < b.len) return b;
if(a.len > b.len) return a;
for(int i = a.len-1;i >= 0;i --) {
if(a.num[i] < b.num[i]) return b;
if(a.num[i] > b.num[i]) return a;
}
return b;
}
//-------------------------------
struct node {
int v,next;
} edge[maxn << 1];
int head[maxn],num = 0;
inline void add_edge(int u,int v) {
edge[++ num].v = v;edge[num].next = head[u];head[u] = num;
} int n;
int siz[maxn];
void dfs(int x,int fa) {
siz[x] = 1;
dp[x][1].len = 1; dp[x][1].num[0] = 1;
for(int i = head[x];i;i = edge[i].next) {
int v = edge[i].v;
if(v == fa) continue;
dfs(v,x);
siz[x] += siz[v];
}
for(int i = head[x];i;i = edge[i].next) {
int v = edge[i].v;
if(v == fa) continue;
for(int i = siz[x];i;-- i) {
if(dp[x][i].len)
for(int j = 1;j <= siz[v];++ j)
if(dp[v][j].len) dp[x][i + j] = max(dp[x][i + j],dp[x][i] * dp[v][j]);
dp[x][i] = dp[x][i] * Max[v];
}
}
for(int i = siz[x];i ;-- i) Max[x] = max(Max[x],dp[x][i] / i);
}
int main() {
n = read();
for(int i = 1,u,v;i < n;++ i) {
u = read();v = read();
add_edge(u,v); add_edge(v,u);
}
dfs(1,0);
Max[1].print();
CF23 E. Tree 树形dp+高精度的更多相关文章
- 熟练剖分(tree) 树形DP
熟练剖分(tree) 树形DP 题目描述 题目传送门 分析 我们设\(f[i][j]\)为以\(i\)为根节点的子树中最坏时间复杂度小于等于\(j\)的概率 设\(g[i][j]\)为当前扫到的以\( ...
- 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: ...
- 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 ...
- codeforces 161D Distance in Tree 树形dp
题目链接: http://codeforces.com/contest/161/problem/D D. Distance in Tree time limit per test 3 secondsm ...
- hdu6035 Colorful Tree 树形dp 给定一棵树,每个节点有一个颜色值。定义每条路径的值为经过的节点的不同颜色数。求所有路径的值和。
/** 题目:hdu6035 Colorful Tree 链接:http://acm.hdu.edu.cn/showproblem.php?pid=6035 题意:给定一棵树,每个节点有一个颜色值.定 ...
- 5.10 省选模拟赛 tree 树形dp 逆元
LINK:tree 整场比赛看起来最不可做 确是最简单的题目. 感觉很难写 不过单独考虑某个点 容易想到树形dp的状态. 设f[x]表示以x为根的子树内有黑边的方案数. 白边方案只有一种所以不用记录. ...
- Codeforces Round #263 Div.1 B Appleman and Tree --树形DP【转】
题意:给了一棵树以及每个节点的颜色,1代表黑,0代表白,求将这棵树拆成k棵树,使得每棵树恰好有一个黑色节点的方法数 解法:树形DP问题.定义: dp[u][0]表示以u为根的子树对父亲的贡献为0 dp ...
- codeforces Round #263(div2) D. Appleman and Tree 树形dp
题意: 给出一棵树,每个节点都被标记了黑或白色,要求把这棵树的其中k条变切换,划分成k+1棵子树,每颗子树必须有1个黑色节点,求有多少种划分方法. 题解: 树形dp dp[x][0]表示是以x为根的树 ...
- POJ 2486 Apple Tree(树形DP)
题目链接 树形DP很弱啊,开始看题,觉得貌似挺简单的,然后发现貌似还可以往回走...然后就不知道怎么做了... 看看了题解http://www.cnblogs.com/wuyiqi/archive/2 ...
随机推荐
- javascript中的this到底指什么?
来自百度知道解释 JavaScript:this是什么? 定义:this是包含它的函数作为方法被调用时所属的对象.说明:这句话有点咬嘴,但一个多余的字也没有,定义非常准确,我们可以分3部分来理解它!1 ...
- node的path.join 和 path.resolve的区别
直接上图: join resolve 明显可以看出,join只会帮你把路径连接起来,而resolve会以当前路径为父路径来把你提供的路径连接起来
- Mysql select id 加上order by 后结果不一致
测试数据将近280万 1.SELECT id FROM cbbd ORDER BY id LIMIT 900000,10 2.SELECT id FROM cbbd LIMIT 900000,10 ...
- [转载]CSS Tools: Reset CSS
http://meyerweb.com/eric/tools/css/reset/ The goal of a reset stylesheet is to reduce browser incons ...
- 关于aspx.designer.cs
.aspx文件..aspx.cs文件和.aspx.designer.cs的一些说明 .aspx文件:(页面)书写页面代码.存储的是页面design代码.只是放各个控件的代码,处理代码一般放在.cs文件 ...
- zTree的简单例子
<%@ page language="java" pageEncoding="UTF-8" %> <%@ include file=" ...
- 微信小程序实现首页图片多种排版布局!
先来个效果图: 使用技术主要是flex布局,绝对定位布局,小程序前端页面开发,以及一些样式! 直接贴代码,都有详细注释,熟悉一下,方便以后小程序开发! wxml: <view class='in ...
- Linux网络状态工具ss命令使用详解【转】
ss命令用于显示socket状态. 他可以显示PACKET sockets, TCP sockets, UDP sockets, DCCP sockets, RAW sockets, Unix dom ...
- 内存溢出(Memory Overflow)和内存泄露(Memory Leak)的区别
内存泄漏指你用malloc或new申请了一块内存,但是没有通过free或delete将内存释放,导致这块内存一直处于占用状态 内存溢出指你申请了10个字节的空间,但是你在这个空间写入11或以上字节的数 ...
- centos6.5环境Redis下载及编译安装
centos6.5环境Redis下载及编译安装 1:官方站点: http://redis.io/download 下载最新版或者最新stable版 2:解压源码并进入目录 tar -zxvf redi ...