`
kenby
  • 浏览: 724274 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

poj 1011 dfs+剪枝

阅读更多

 

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#define DEBUG

#ifdef DEBUG
#define debug(...) printf( __VA_ARGS__) 
#else
#define debug(...)
#endif

int		n, len, count;
char 	found;
int 	stick[64];
int		st[64];		/* st[k] = sum{a[k]...a[n-1]}, 某根木棒和所有比它短的木棒加起来的长度 */
char 	used[64];

static int 
compare(const void *p1, const void *p2)
{
	return *((int *)p2) - *((int *)p1);
}

/* 第k个小木棒开始搜索, sum:木棒还原好的长度, num: 已还原好的木棒数 */
void 
dfs(int k, int sum, int num) 
{
	int 	i, pre;

	if (num == count) {
		found = 1;
		return;
	}
	if (sum == len) {
		dfs(0, 0, num+1);
	}
	else {
		//从第k跟木棒开始搜索,如果有一根木棒满足:
		//1 未被使用
		//2 之前没有相同长度的木棒出现过
		//3 它的长度加上已拼凑好的长度不会超过原始长度
		//4 sum加上它自己和所有比它短的木棒的长度必须超过原始长度
		//则把这根木棒拼凑过去
		for (pre = -1, i = k; i < n; i++) {
			if (!used[i] && stick[i] != pre && sum+stick[i] <= len && sum+st[i] >= len) {
				pre = stick[i];
				debug("选择%d加在第%d根木棒\n", stick[i], num+1);
				used[i] = 1;
				dfs(i+1, sum+stick[i], num);
				if (found) return;
				debug("否定%d\n", stick[i]);
				used[i] = 0;
				if (k == 0) break;	/* 原始木棒的第1根木棒总是用长度最大的, 不用往后找 */
			}
		}
	}
}

int 
main()
{
	int		i, j, k, sum;

	while (scanf("%d", &n), n != 0) {
		sum = 0;
		found = 0;
		for (i = 0; i < n; i++) {
			scanf("%d", stick+i);
			sum += stick[i];
		}
		qsort(stick, n, sizeof(int), compare);
		st[n-1] = stick[n-1];
		for (i = n-2; i >= 0; i--) {
			st[i] = st[i+1]+stick[i];
		}
		for (i = stick[0]; i <= sum; i++) {
			if (sum % i == 0) {
				debug("----------长度为%d的搜索过程------------\n", i);
				len = i;
				count = sum/i;
				memset(used, 0, sizeof(used));
				dfs(0, 0, 0);

				debug("还原结果为: ");
				for (k = 0; k < n; k++) {
					debug("%d ", used[k]);
				}
				debug("\n\n");

				if (found) {
					break;
				}
			}
		}
		printf("%d\n", found? len : sum);
	}
	return 0;
}
分享到:
评论

相关推荐

    POJ3009-Curling 2.0【DFS+Vector+回溯+剪枝】

    提供的代码文件"POJ3009-Curling 2.0【DFS+Vector+剪枝】.cpp"和"POJ3009-Curling 2.0【DFS+回溯+剪枝】.cpp"应该分别展示了如何在实际编程中应用这些技术,而"POJ3009-Curling 2.0.doc"则可能是解题报告,详细阐述...

    POJ3373-Changing Digits【DFS+强剪枝】

    标题“POJ3373-Changing Digits【DFS+强剪枝】”涉及的是一个编程竞赛中的问题,这个问题在北大POJ(北京大学在线评测系统)平台上被提出。"Changing Digits"是一个算法挑战,而解决方案是通过深度优先搜索(DFS)...

    POJ3733-Changing Digits【DFS+强剪枝】

    【标题】"POJ3733-Changing Digits【DFS+强剪枝】"是一个来自北京大学在线评测系统POJ的编程题目,该题目主要涉及深度优先搜索(DFS)算法和强剪枝策略。在算法竞赛和编程挑战中,这类问题通常要求参赛者通过编写...

    LeetCode判断字符串是否循环-Leetcode:刷!

    1011(搜索+剪枝) POJ 1416 POJ 2676 POJ 1129:white_question_mark: 数据结构 串 POJ 1016 POJ 1035 POJ 3080 POJ 1936 排序(快排) POJ 1007 POJ 2388 POJ 1804 POJ 2299 高效查找 POJ 1002 POJ 3349 POJ 3274 ...

    POJ1020-Anniversary Cake【有技巧的DFS】

    【标题】"POJ1020-Anniversary Cake【有技巧的DFS】"是一个源自北京大学在线编程平台POJ的编程题目,它涉及到深度优先搜索(DFS)算法的应用。这道题目要求参赛者通过编程解决一个有趣的问题,即在特定条件下如何...

    poj各种分类

    包括深度优先遍历(DFS)和广度优先遍历(BFS),用于探索图的所有节点,是解决许多图问题的基础,如poj1860和poj3259所示。 #### 最短路径算法 Dijkstra算法、Bellman-Ford算法和Floyd算法分别适用于无负权边、有...

    深搜宽搜与剪枝分析与poj具体程序举例

    本文主要探讨了两种基础的搜索算法——深度优先搜索(DFS)和宽度优先搜索(BFS),以及剪枝策略,并通过POJ平台上的实例进行了分析。 1. **搜索算法基本概念** - **状态(state)**:表示问题在某个时间点的进展...

    POJ2676-Sudoku

    标题“POJ2676-Sudoku”指向的是北京大学在线编程平台POJ上的一道题目,编号为2676,题目内容与经典的数独游戏有关。解题报告和AC(Accepted)代码是该问题解决方案的组成部分,通常包括对问题的理解、算法设计、...

    acm poj300题分层训练

    5. **搜索算法的优化**:poj1699、poj3411等训练搜索技巧和剪枝方法,poj3373、poj1691则介绍了记忆化搜索。 6. **更复杂的动态规划**:poj1191、poj1054等题目增加了动态规划的难度,引入了记录状态的DP和树型DP。 ...

    算法竞赛专题解析--搜索进阶(2)剪枝1

    2. DFS剪枝则更加多样化,包括: - 可行性剪枝:在遇到非法状态时立即终止搜索。 - 最优性剪枝:在最优化问题中,如果当前路径的代价超过了已找到的最优解,就无需继续该分支。 - 搜索顺序剪枝:通过改变搜索顺序...

    POJ 1077 算法

    这是一个典型的图搜索问题,常见的解决方法包括深度优先搜索(DFS)、广度优先搜索(BFS)以及A*搜索算法。 在八数码问题中,我们需要定义数据结构来表示当前的状态,通常是一个9个元素的一维数组,其中0代表空白...

    poj2488.rar_poj24_poj2488_方向模板法

    标题中的“poj2488.rar_poj24_poj2488_方向模板法”指的是一个解决编程竞赛问题POJ2488的压缩文件,其中可能包含了解决该问题的代码示例。POJ是Programming Online Judge的缩写,是一个在线的编程竞赛平台,参与者...

    poj题目分类

    3. 搜索技巧与剪枝:优化搜索效率,如POJ2531、POJ1416。 五、动态规划 1. 背包问题:如POJ1837、POJ1276,涉及0-1背包、完全背包等。 2. 表达式DP:常见于解决组合优化问题,如矩阵链乘法。 以上只是POJ题目分类...

    POJ2488-A Knight's Journey【骑士游历】

    6. **剪枝**:为了提高效率,可以设计剪枝条件,例如在搜索过程中,如果发现当前路径无法形成完整的遍历,就立即停止该路径的搜索,转向其他可能性。 7. **代码实现**:提供的源文件`POJ2488-A Knight's Journey....

    poj大量习题详解ACM

    1. **基础算法**:如排序算法(快速排序、归并排序、堆排序等)、搜索算法(深度优先搜索DFS、广度优先搜索BFS)、图论算法(最短路径Dijkstra、Floyd、Bellman-Ford)、动态规划(状态转移方程、剪枝技术等)、回溯...

    POJ 分类题目

    - **定义**:包括深度优先遍历(DFS)和广度优先遍历(BFS)。 - **示例题目**: - poj1426 - poj3126 - poj2251 - poj2243 - poj3352 - poj1111 - poj3051 - poj1129 - poj2907 - **应用场景**:适用于...

    poj 1000 - 2000 部分题目 官方分类

    6. **回溯与分支限界**:这类题目涉及到深度优先搜索和广度优先搜索,以及如何有效地剪枝来避免无效计算。 7. **图算法**:图论是计算机科学中的一大分支,题目可能涵盖DFS、BFS、最小生成树、最短路径等算法。 8....

    POJ 3009 Curling 2.0 解题报告

    ### POJ 3009 Curling 2.0 解题报告 #### 问题描述与分析 本题属于经典的搜索类题目,要求我们利用给定的规则在一个类似于网格的地图上移动一个石头,从起点到达终点,并求出最少的步数。地图上除了起点和终点外,...

    acm程序设计竞赛深度搜索DFS实例

    2. **最短路径**:虽然Dijkstra算法和Bellman-Ford算法更适合求解最短路径,但在特定情况下,DFS结合剪枝策略也能找出某些情况下的最短路径。 3. **拓扑排序**:在无环有向图(DAG)中,DFS可以进行拓扑排序,将所有...

Global site tag (gtag.js) - Google Analytics