Life is short, so we need program

每日一题, 积累从点滴开始

  :: 首页 :: 博问 :: 闪存 :: :: 联系 :: :: 管理 ::

zju1037-Gridland(解题来自《ACM国际大学生程序设计竞赛题解(1)》

【题目大意】

背景:

  多年来,计算机科学家一直在寻找有效的方法来解决困难的计算机问题。有些问题已经找到了有效的算法,如排序、计算多边形面积、寻找图的最短路径,这些都是“容易的”问题。而“困难的”问题,目前只有计算时间是指数级的算法,旅行售货员的问题就是其中之一。给出N个城市,及城市之间的道路,问题是寻找一条最短的路径,让售货员访问每一个城市一次且只有一次,又回到出发点。

问题:

  Gridland的总统雇佣你来编写一个程序,计算在这个国家中所有城市的旅行售货员问题的最短长度。在Gridland,每个城市都位于矩形网格的一个点上。通向每个城市的道路只有东、西、南、北、东南、东北、西南和西北方向,在每个方向上只有一个相邻的城市。东西、南北方向的长度为1,长度单位是欧几里得距离。如图(图略)所示是一个2*3的Gridland,最短的环游路线长度是6。

输入:

  第一行是测试列数。

  每个测试例,在一行里有两个整数m和n(1<m,n<50),中间有一个空格,是二维栅格的大小。

输出:

  对每个测试例,第一行输出:“Scenario #i:",i是从1开始的测试例编号。第二行输出售货员环游问题的最短长度,精确到两位小数。每个测试例之后又一个空行。

【算法分析】

  题目中一直强调旅行售货员问题,容易诱导竞赛者去使用复杂的算法,如回溯算法、分支限定算法。而本题的城市位置是特殊的,边长也是特殊的,所以能够寻找简单的规律进行计算。 

  网友Winsty给出了一个简捷的算法,当m或n为偶数时,最短长度为mn;当m和n同时为技术时,最短路长度为mn再加0.41,因为要走一个斜边。图略。

代码如下:

 

#include <iostream>
#include <cstdio>
using namespace std;

int main()
{
	int n;
	int i=1;
	scanf("%d",&n);
	while(n--)
	{
		int a,b;
		scanf("%d%d",&a,&b);
		printf("Scenario #%d:\n",i++);
		printf("%d",a*b);
		if(a%2&&b%2)
		printf(".41");
		else
		printf(".00");
		printf("\n\n");
	}
	return 0;
}

 

posted on 2013-05-07 23:03  CDU_ICPC  阅读(530)  评论(0编辑  收藏  举报