(中等) 树形dp HOJ 2178 Optical Fiber
来源:互联网 发布:碧柔防晒知乎 编辑:程序博客网 时间:2024/06/06 00:39
Optical Fiber
Submitted : 63, Accepted : 39
A far away developing country is trying to improve its communication infrastructure. Currently, each city in the country has its local computer network, but there is no fast communication between the cities. The Autonomous Communications Ministry (ACM) of the country decided to create a fast, optical fiber network connecting every city. In order to do this, they decided to take the following approach. Pairs of cities were chosen to have an optical fiber link installed between them. The choice was such that there will be only one fiber path between any pair of cities, in order to reduce the cost. The pairs of cities were chosen considering many factors, including analysis of estimated demand and distance between the cities.
Each city will have one optical router installed, which will be used to connect all the optical links with one end in that city. In each city, there are many different locations where the optical router can be installed. Your task, as an engineer working on this project, is to develop a computer program to pick up the locations in each city in order to minimize the total length of fiber that will be necessary for this project.
Input
The input consists of multiple test cases. Each test case starts with a line containing the number of cities N (1 <= N <= 1000) in the country. Following, for each city, there is a sequence of lines. The first line contains the (unique) name of the city (only capital letters, at most 15), and the number of candidate sites Ci (1 <= Ci <= 50) where the optical router can be installed. Then, there is one line per candidate site, containing two integers X and Y representing the coordinates of the site (-10000 <= X, Y <= 10000). You should use the euclidean distance between the sites to compute the corresponding fiber length necessary to connect them. After the description of each city with its candidate sites, there are N - 1 lines, each containing the names of two cities that will have a fiber link installed between them. The end of the input is indicated by N = 0.
Output
For each test case, your program should print a line with the minimum total length of optical fiber to connect the requested cities. Your answer should be rounded to one decimal digit.
Sample Input
3AUSTIN 1500 500DALLAS 21000 10990 -10ELPASO 20 030 0ELPASO AUSTINDALLAS ELPASO3HUSTON 3100 0100 50100 100AUSTIN 2200 0180 40SANANTONIO 20 -1010 -50HUSTON AUSTINHUSTON SANANTONIO0
Sample Output
1646.3189.9
题意:有n个城市,城市中有一些location,现在想要在每个城市中选定一个location然后把城市连接起来,使得城市之间通过一定的方式相连,使得任意的两个城市之间存在且仅存在一条路径,并且求出最短的路径。
思路:根据题目的意思,我们把每个城市画出来,用一个圈表示,然后每个城市里面都包含一些节点,然后城市与城市之间根据题目给的连接情况连接起来,那么这是一棵树。怎么样,如果你做过一些树形dp的题目的话,见到这个图后思路应该马上就来了吧。这里麻烦的只是建图。我们把每个城市从1~n进行标号。所有城市包含的成员节点从1~nn。那么在遍历图的时候按1~n这个遍历。dp的时候按1~nn来dp,动态方程见代码
代码:
#include<iostream>
#include<cstring>
#include<algorithm>
#include<math.h>
#include<map>
#include<cstdio>
#include<queue>
#include<string.h>
#include<vector>
#include<stack>
#include<string>
using namespace std;
#define mp make_pair
#define eps 1e-8
const int maxn = 1000+10;
const int inf = 1e9;
#define LL long long
vector<int> node[maxn];
map<string,int> name;
int n , m , nn;
char buffer[20];
char buffer1[20];
double dp[maxn*50];
struct Edge
{
int v;
Edge *next;
} *first[maxn] , edge[2*maxn];
void add(int x,int y)
{
edge[++m].v = y;
edge[m].next = first[x];
first[x] = &edge[m];
}
struct Point
{
int x , y;
} pt[maxn*50];
double sqr(double x)
{
return x*x;
}
double cal_dis(Point p1,Point p2)
{
return sqrt( sqr(p1.x-p2.x)+sqr(p1.y-p2.y));
}
void init()
{
m = 0 , nn=1;
memset(first,0,sizeof(first));
memset(dp,0,sizeof(dp));
name.clear();
for (int i = 1 ; i <= n ; ++i) node[i].clear();
}
void input()
{
for (int i = 1 ; i <= n ; ++i)
{
scanf("%s",buffer);
string s = buffer;
name[s] = i;
int C;
scanf("%d",&C);
while (C--)
{
scanf("%d%d", &pt[nn].x , &pt[nn].y);
node[i].push_back(nn);
++nn;
}
}
for (int i = 1 ; i < n ; ++i)
{
scanf("%s%s",buffer,buffer1);
string s1 = buffer , s2 = buffer1;
int u = name[s1];
int v = name[s2];
add(u,v);
add(v,u);
}
}
void tp(int x,int fa)
{
Edge *p = first[x];
while (p)
{
int y = p->v;
if (y!=fa)
{
tp(y,x);
for (int i = 0 ; i < node[x].size() ; ++i)
{
int ii = node[x][i];
double tem = inf;
for (int j = 0 ; j < node[y].size() ; ++j)
{
int jj = node[y][j];
double dis = cal_dis(pt[ii],pt[jj]);
if (tem > dp[jj]+dis)
tem = dp[jj]+dis;
}
dp[ii] += tem;
}
}
p = p->next;
}
}
void solve()
{
tp(1,-1);
double ans = inf;
for (int i = 0 ; i < node[1].size() ; ++i)
{
int ii = node[1][i];
if (dp[ii] < ans) ans = dp[ii];
}
printf("%.1lf\n",ans+eps);
}
int main()
{
while (scanf("%d",&n) , n)
{
init();
input();
solve();
}
}
- (中等) 树形dp HOJ 2178 Optical Fiber
- *(中等) dp HOJ 2133 Tourist
- 光纤通信(Optical Fiber Communication)
- (中等) 树形dp POJ 1155 TELE
- *(中等) 树形dp POJ 2486 Apple Tree
- (中等) 状态压缩dp HOJ 1894 Islands and Bridges
- (中等) 状态压缩dp HOJ 2480 The best travel design
- (中等) 状态压缩dp HOJ 2193 Time to Graduate
- (简单)树形dp HOJ 2514 Perfect Service
- (中等) 树形dp(分组背包) POJ 3345 Bribing FIPA
- (简单) 树形dp HOJ 2500 Party at Hali-Bula
- (中等) 搜索 HOJ 1049 sticks
- ZOJ 3824Fiber-optic Network 树形dp 2014牡丹江现场赛F
- Optical Fiber Telecommunications V A, Fifth Edition: Components and Subsystems
- Optical Fiber Telecommunications V B, Fifth Edition: Systems and Networks
- *(中等) 树形dp+分组背包 HDU 4276 The Ghost Blows Light
- (中等)动态规划Hoj 1719 Spiderman
- (中等) 最短路 HOJ 2132 Easter holidays
- (简单) dp HOJ 2091 Chess
- (简单) 博弈 HOJ 2128 S-Nim
- (中等) 最短路 HOJ 2132 Easter holidays
- Android之菜单一——选项菜单
- (中等) 动态规划 HOJ 2177 ICPC Strikes Again
- (中等) 树形dp HOJ 2178 Optical Fiber
- (简单) 不需要算法 HOJ 1019 Grandpa\'s Other Estate
- *数论 HOJ 3110 Remoteland
- 博弈论 HOJ 1122 Number Game
- 字符串(最小表示法) HOJ 1223 Hidden Password
- 搜索 HOJ 1266 Phone Home
- 搜索 HOJ 1281 Lagrange\'s Four-Square Theorem
- *搜索 HOJ 1320 Square Destroyer
- 概率dp ZOJ 3640 Help Me Escape
程序博客网,程序员的互联网技术博客家园。csdn论坛精品 msdn技术资料都在这里