题目链接:http://acm.timus.ru/problem.aspx?space=1&num=1210
题目描述:有向加权图的底层最短距离;大意是:从第一层的一个节点开始,只能沿已有的路径网上一层的某个节点前进,路径是加权的,可以是负值;求到达最后一层的最短权重和;
思路大致就是一点点变形的动态规划,一层一层地用贪心算法找上去;
直接上AC代码:
#define _CRT_SECURE_NO_WARNINGS
#include <iostream>
#include <stdio.h>
#include <string>
#include <algorithm>
#include <vector>
#include <queue>
#include <cmath>
#include <map>
using namespace std;
const int MAX_VALUE = 99999999;
struct Rout{
int num;
int cost;
};
struct Node{
vector<Rout>v;
int cost;
};
void func(){
vector<vector<Node> >v;
vector<Node>vLine;
Node node;
node.cost = 0;
vLine.push_back(node);
v.push_back(vLine); //第0层初始化,cost为0
vLine.clear();
node.cost = MAX_VALUE;
int level, n;
cin >> level;
for (int i = 0; i < level; i++){ //创建每一层的同时,为前一层搭建路径
cin >> n;
vLine.resize(n,node);
v.push_back(vLine);
for (int j = 0; j < n; j++){
int num, dis;
Rout rout;
while (cin >> num&&num){
cin >> dis;
rout.num = j;
rout.cost = dis;
v[i][num - 1].v.push_back(rout);
}
}
if (i < level - 1){ //莫名其妙的星字符
char symbol;
cin >> symbol;
}
}
for (int i = 0; i < level; i++){ // 一层一层找当前最短路径cost,并保存在该层节点上
int len = v[i].size();
for (int j = 0; j < len; j++){
vector<Rout> &tmp = v[i][j].v;
for (size_t k = 0; k < tmp.size(); k++){
int num = tmp[k].num;
int cost = tmp[k].cost;
if (v[i + 1][num].cost>cost + v[i][j].cost)
v[i + 1][num].cost = cost + v[i][j].cost;
}
}
}
int ans = MAX_VALUE;
for (size_t i = 0; i < v[level].size(); i++){
ans = ans < v[level][i].cost ? ans : v[level][i].cost;
}
cout << ans << endl;
}
int main(){
freopen("out.txt", "w", stdout);
freopen("in.txt", "r", stdin);
func();
}