Sticks

Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)
Total Submission(s): 13807    Accepted Submission(s): 4270

Problem Description
George took sticks of the same length and cut them randomly until all parts became at most 50 units long. Now he wants to return sticks to the original state, but he forgot how many sticks he had originally and how long they were originally. Please help him and design a program which computes the smallest possible original length of those sticks. All lengths expressed in units are integers greater than zero. 
 
Input
The input contains blocks of 2 lines. The first line contains the number of sticks parts after cutting, there are at most 64 sticks. The second line contains the lengths of those parts separated by the space. The last line of the file contains zero.
 
Output
The output file contains the smallest possible length of original sticks, one per line. 
 
Sample Input
9
5 2 1 5 2 1 5 2 1
4
1 2 3 4
0
 
Sample Output
6
5

我做的第二道dfs题。。。

题意:给出n个小木棒的长度,他们是又数根长度相同的木棒剪短得来的,问没剪短之前的木棒长度最短是多少

题解:要把这些小木棒拼接成数根长度相同的长木棒。要用到搜索算法。但因为搜索算法时间复杂度较高,需要剪枝才行。可以先给小木棒从大到小排个序,最后拼成的长木棒长度肯定在小木棒长度最大值和所有小木棒加起来的长度之间(因为是拼起来的,不可能比原来小木棒还短)。然后判断小木棒长度总和与假设的长木棒原长是不是整除关系。是的话就按照这个假设长度搜索,看不能全部拼成。

 #include<bits/stdc++.h>
using namespace std;
const int maxn = ;
const int INF = 0x3f3f3f3f;
int n, sumv, target, aim;//target表示目标的棍子个数,aim表示目标的棍子长度,sumv为所有木棍总长度
int stick[maxn], vis[maxn];//vis数组标记 ,stick存储输入的木棒长度
bool cmp(int a, int b) {
return a > b;
}
bool dfs(int cnt, int len, int pos) {
if(cnt == target) return true;//根数对上就返回 退出dfs
if(len == aim) return dfs(cnt+, , ); //当拼完一根后,继续拼下一根
for(int i = pos; i < n; i++) {//从大到小排序后,按顺序搜索
if(!vis[i] && len+stick[i] <= aim) {
vis[i] = ;
if(dfs(cnt, len+stick[i], i+)) return true;
vis[i] = ; //只有失败才会运行到下面,否则是直接返回的
if(len == ) return false; //如果第一根时失败 剪枝
while(i+ < n && stick[i+] == stick[i]) i++; //如果下一根长度跟当前的失败的长度一样,剪枝
}
}
return false;
}
int main() {
while(~scanf("%d", &n), n) {
sumv = ;
for(int i = ; i < n; i++) {
scanf("%d",&stick[i]);
sumv += stick[i];
}
sort(stick, stick+n, cmp);
int ans = ;
for(int i = stick[]; i <= sumv; i++) {//拼好后的木棒长度只会在stick[0]和总长度之间
if(sumv % i == ) {
memset(vis, , sizeof(vis));
aim = i;
target = sumv / aim;
if(dfs(, , )) {
ans = aim;
break;
}
}
}
printf("%d\n",ans);
}
return ;
}

hdu1455Sticks(经典dfs+剪枝)的更多相关文章

  1. poj 1011 :Sticks (dfs+剪枝)

    题意:给出n根小棒的长度stick[i],已知这n根小棒原本由若干根长度相同的长木棒(原棒)分解而来.求出原棒的最小可能长度. 思路:dfs+剪枝.蛮经典的题目,重点在于dfs剪枝的设计.先说先具体的 ...

  2. poj1011(DFS+剪枝)

    题目链接:https://vjudge.net/problem/POJ-1011 题意:给定n(<=64)条木棍的长度(<=50),将这些木棍刚好拼成长度一样的若干条木棍,求拼出的可能的最 ...

  3. *HDU1455 DFS剪枝

    Sticks Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Subm ...

  4. POJ 3009 DFS+剪枝

    POJ3009 DFS+剪枝 原题: Curling 2.0 Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 16280 Acce ...

  5. poj 1724:ROADS(DFS + 剪枝)

    ROADS Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 10777   Accepted: 3961 Descriptio ...

  6. DFS(剪枝) POJ 1011 Sticks

    题目传送门 /* 题意:若干小木棍,是由多条相同长度的长木棍分割而成,问最小的原来长木棍的长度: DFS剪枝:剪枝搜索的好题!TLE好几次,终于剪枝完全! 剪枝主要在4和5:4 相同长度的木棍不再搜索 ...

  7. DFS+剪枝 HDOJ 5323 Solve this interesting problem

    题目传送门 /* 题意:告诉一个区间[L,R],问根节点的n是多少 DFS+剪枝:父亲节点有四种情况:[l, r + len],[l, r + len - 1],[l - len, r],[l - l ...

  8. HDU 5952 Counting Cliques 【DFS+剪枝】 (2016ACM/ICPC亚洲区沈阳站)

    Counting Cliques Time Limit: 8000/4000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others) ...

  9. HDU 5937 Equation 【DFS+剪枝】 (2016年中国大学生程序设计竞赛(杭州))

    Equation Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total S ...

随机推荐

  1. hbase添加大文件

    一直使用hbase作大容量存储,因为hbase易于存取. 今天,在录入数据的时候,突然报出一个KeyValue size too large.很是奇怪. 后来发现,该数据特别大,经查源码 privat ...

  2. 使用jQuery实现伪分页

    在之前的项目中遇到一个这样的问题,页面分为上下两部分(分别称为未选中设备信息部分和选中设备信息部分),上面是从数据库拿出来的所有的设备信息,下面是显式已选中的设备信息,页面如下所示: 可以选中其中的任 ...

  3. java之sleep(),join(),yield(),wait(),notify()、notifyAll()区别

    1.sleep() 使当前线程(即调用该方法的线程)暂停执行一段时间,让其他线程有机会继续执行,但它并不释放对象锁.也就是说如果有synchronized同步快,其他线程仍然不能访问共享数据.注意该方 ...

  4. C语言中内存分配

     C语言中内存分配   在任何程序设计环境及语言中,内存管理都十分重要.在目前的计算机系统或嵌入式系统中,内存资源仍然是有限的.因此在程序设计中,有效地管理内存资源是程序员首先考虑的问题. 第1节主要 ...

  5. C++备忘知识整理

    一.设置字体颜色 C++控制台程序运行时输出框默认的文字颜色是白色,所以我常称其输出框为黑白框.但是这个文字样式不是固定不变的,是可以改变颜色的字体的.方法有两种: 1.设置输出框的框体属性.在运行时 ...

  6. SQL 二

    1.执行DML语句的步骤:在数据库缓冲区缓存中搜索相关的块:将块从数据文件复制到缓冲区:将变更向量写入日志缓冲区:将变更向量应用于数据库缓冲区缓存.2.重做可以保护的段类型:索引段.表段.撤销段.3. ...

  7. 基于多用户的Oracle数据泵导入导出数据

    登陆SqlPlus: SqlPlus sys/syspwd@MyOrcl AS sysdba 其中:syspwd:sys的登陆密码:MyOrcl:所创建的数据库服务名. 创建数据泵: create o ...

  8. 如何优雅的使用C语言绘制一只小猪佩奇

    今天我们来用C语言画一只小猪佩奇---社会.社会....在画小猪佩奇之前,我们先使用带符号的距离长 (signed distance field,SDF) 来画一个圆形. 使用这个方法表示形状,但是这 ...

  9. pt-online-schema-change在线修改表结构

    工具简介 pt-osc模仿MySQL内部的改表方式进行改表,但整个改表过程是通过对原始表的拷贝来完成的,即在改表过程中原始表不会被锁定,并不影响对该表的读写操作.首先,osc创建与原始表相同的不包含数 ...

  10. linux 学习第七天

    一.bash 使用(for循环.while循环) 1.1.批量添加用户 1.2.查看用户是否存在 A.cut -d : -f 1 /etc/passwd B.id dream  (id 用户名称) C ...