如果知道了树的形态,那么可以树形DP,每个时刻只需要计算必选根的独立集个数以及必不选根的独立集个数。

那么现在知道独立集个数,要构造出树,可以考虑DP这棵树的形态,然后将之前树形DP的值作为现在DP的状态,即$dp[i][j]$表示必选根的独立集个数为$i$,必不选根的独立集个数为$j$时,树的节点数最少是多少。

那么完成这个DP之后,输出方案只需要沿着最优值来的顺序dfs输出即可。

#include<stdio.h>
#include<algorithm>
#include<math.h>
#include<string.h>
#include<string>
#include<vector>
#include<set>
#include<map>
#include<queue>
#include<time.h>
#include<assert.h>
#include<iostream>
using namespace std;
typedef long long LL;
typedef pair<int,int>pi;
const int Inf=100;
int cnt;
int dp[2020][2020];
struct Node{
short i,j,x,y;
Node(){}
Node(short i,short j,short x,short y):i(i),j(j),x(x),y(y){}
};
Node pre[2020][2020];
void dfs(int u,int x,int y){
if(x==1&&y==1)return ;
//printf("x=%d y=%d\n",x,y);
dfs(u,pre[x][y].i,pre[x][y].j);
++cnt;
printf("%d %d\n",u,cnt);
dfs(cnt,pre[x][y].x,pre[x][y].y);
}
vector<int>V[3000];
int main(){
int tl=0;
for(int i=1;i<=2005;i++){
for(int j=i;j<=2005;j+=i)V[j].push_back(i);
}
for(int i=0;i<2020;i++)for(int j=0;j<2020;j++)dp[i][j]=Inf;
dp[1][1]=1;
for(int i=1;i<=2005;i++){
for(int j=1;j<=2005;j++){
if(dp[i][j]>15)continue;
for(int y=1;y*i<=2005;y++){
for(int x=1;(x+y)*j<=2005;x++){
int tmp=dp[i][j]+dp[x][y];
int nx=y*i,ny=j*(x+y);
if(dp[nx][ny]>tmp){
dp[nx][ny]=tmp;
pre[nx][ny]=Node(i,j,x,y);
}
tl++;
}
}
for(int y=1;y*(i+j)<=2005;y++){
for(int x=1;x*j<=2005;x++){
int tmp=dp[i][j]+dp[x][y];
int nx=j*x,ny=y*(i+j);
if(dp[nx][ny]>tmp){
dp[nx][ny]=tmp;
pre[nx][ny]=Node(x,y,i,j);
}
tl++;
}
} }
}
/*
for(int nx=1;nx<=2005;nx++){
for(int ny=1;ny<=2005;ny++){
if(nx==1&&ny==1){dp[nx][ny]=1;continue;}
for(int it1=0;it1<V[nx].size();it1++){
for(int it2=0;it2<V[ny].size();it2++){
int i=V[nx][it1],j=V[ny][it2];
int y=nx/i,x=ny/j-y;
if(x>=1&&y>=1&&dp[i][j]+dp[x][y]<dp[nx][ny]){
dp[nx][ny]=dp[i][j]+dp[x][y];
pre[nx][ny]=Node(i,j,x,y);
}
tl++;
}
}
}
}
*/
//printf("tl=%d\n",tl);
int _;scanf("%d",&_);
while(_--){
int m;
scanf("%d",&m);
//for(int tm=1;tm<=2000;tm++){
// m=tm+1;
m++;
bool flag=0;
int sx=-1,sy;
for(int i=0;i<=m;i++){
if(dp[i][m-i]<=15){
sx=i;sy=m-i;
break;
}
}
if(sx<0)puts("-1");
else{
printf("%d\n",dp[sx][sy]);
cnt=1;
dfs(1,sx,sy);
}
}
return 0;
}

  

ZOJ3951 : Independent Set的更多相关文章

  1. 写一个程序可以对两个字符串进行测试,得知第一个字符串是否包含在第二个字符串中。如字符串”PEN”包含在字符串“INDEPENDENT”中。

    package lovo.test; import java.util.Scanner; public class Java { @param args public static void main ...

  2. Deep Learning 13_深度学习UFLDL教程:Independent Component Analysis_Exercise(斯坦福大学深度学习教程)

    前言 理论知识:UFLDL教程.Deep learning:三十三(ICA模型).Deep learning:三十九(ICA模型练习) 实验环境:win7, matlab2015b,16G内存,2T机 ...

  3. [ZZ] KlayGE 游戏引擎 之 Order Independent Transparency(OIT)

    转载请注明出处为KlayGE游戏引擎,本文的永久链接为http://www.klayge.org/?p=2233 http://dogasshole.iteye.com/blog/1429665 ht ...

  4. Andrew Ng机器学习公开课笔记–Independent Components Analysis

    网易公开课,第15课 notes,11 参考, PCA本质是旋转找到新的基(basis),即坐标轴,并且新的基的维数大大降低 ICA也是找到新的基,但是目的是完全不一样的,而且ICA是不会降维的 对于 ...

  5. Questions that are independent of programming language. These questions are typically more abstract than other categories.

    Questions that are independent of programming language.  These questions are typically more abstract ...

  6. Interview-Largest independent set in binary tree.

    BT(binary tree), want to find the LIS(largest independent set) of the BT. LIS: if the current node i ...

  7. 【转】NDK编译可执行文件在Android L中运行显示error: only position independent executables (PIE) are supported.失败问题解决办法。

    原文网址:http://blog.csdn.net/hxdanya/article/details/39371759 由于使用了NDK编译的可执行文件在应用中调用,在4.4及之前的版本上一直没出问题. ...

  8. 基于Hama并联平台Finding a Maximal Independent Set 设计与实现算法

    笔者:白松 NPU学生. 转载请注明出处:http://blog.csdn.net/xin_jmail/article/details/32101483. 本文參加了2014年CSDN博文大赛,假设您 ...

  9. More than one file was found with OS independent path 錯誤

    More than one file was found with OS independent path 'lib/armeabi/libmrpoid.so',. 翻譯過來就是:在操作系統的獨立目錄 ...

随机推荐

  1. Left-pad

    L1-032 Left-pad (20 分)   根据新浪微博上的消息,有一位开发者不满NPM(Node Package Manager)的做法,收回了自己的开源代码,其中包括一个叫left-pad的 ...

  2. 变相实现textarea文本域

    效果图: html: <div> <form action=""> <div class="ta-div" contentedit ...

  3. IntelliJ IDEA 中自动生成 serialVersionUID 的方法

    as, idea plugin中搜如下关键字,并安装该插件: GenerateSerialVersionUID 如上图所示,创建一个类并实现Serializable接口,然后按alt+Enter键,即 ...

  4. Java中的IO流总结

    Java中的IO流总结 1. 流的继承关系,以及字节流和字符流. 2. 节点流FileOutputStream和FileInputStream和处理流BufferedInputStream和Buffe ...

  5. SignalRMvc的简单例子

    1.介绍 我们知道传统的http采用的是“拉模型”,也就是每次请求,每次断开这种短请求模式,这种场景下,client是老大,server就像一个小乌龟任人摆布,很显然,只有一方主动,这事情就没那么完美 ...

  6. Ncurses - Panel

    当你需要创建许多窗口时,你很快就会发现它们会变得难以管理.Panel library提供了很好的解决方案. Panel 实际上是一个窗口,通过容器 - 栈 来管理,栈顶的 panel 是完全可见的,其 ...

  7. java数组知识点总结

    数组是一个用来存储同一个数据类型多个元素的一个容器(数组长度是固定的,数组中存储的元素的数据类型要求一致) 1.格式: 格式1: 数据类型[] 数组名 = new 数据类型[数组长度]; 格式2: 数 ...

  8. jquery实时监听输入框值变化

    在做web开发时候很多时候都需要即时监听输入框值的变化,以便作出即时动作去引导浏览者增强网站的用户体验感.而采用onchange时间又往往是在输入框失去焦点(onblur)时候触发,有时候并不能满足条 ...

  9. Codeforces 837F Prefix Sums

    Prefix Sums 在 n >= 4时候直接暴力. n <= 4的时候二分加矩阵快速幂去check #include<bits/stdc++.h> #define LL l ...

  10. Thinkphp3.1 php 链接SqlServer

    ThinkPHP链接 M("lk_employeeInfo","Null/表前缀","sqlsrv://账号:密码@服务器:端口/数据库") ...