hdu 4360 As long as Binbin loves Sangsang
Description
Binbin misses Sangsang so much. He wants to meet with Sangsang as soon as possible.
Now Binbin downloads a map from ELGOOG.There are N (1<=N<=1,314) cities in the map and these cities are connected by M(0<=M<=13,520) bi-direct roads. Each road has a length L (1<=L<=1,314,520)and is marked using a unique ID, which is a letter fromthe string “LOVE”!
Binbin rides a DONKEY, the donkey is so strange that it has to walk in the following sequence ‘L’->’O’->’V’->’E’->’L’->’O’->’V’->’E’->…. etc.
Can you tell Binbin how far the donkey has to walk in order to meet with Sangsang?
WARNING: Sangsang will feel unhappy if Binbin ride the donkey without a complete”LOVE” string.
Binbin is at node 1 and Sangsang is at node N.
Input
The first line has an integer T(1<=T<=520), indicate how many test cases bellow.
Each test case begins with two integers N, M (N cities marked using an integer from 1…N and M roads).
Then following M lines, each line has four variables“U V L letter”, means that there is a road between city U,V(1<=U,V<=N) with length L and the letter marked is‘L’,’O’,’V’ or ‘E’
Output
For each test case, output a string
1. “Case ?: Binbin you disappoint Sangsang again, damn it!”
If Binbin failed to meet with Sangsang or the donkey can’t finish a path withthe full “LOVE” string.
2. “Case ?: Cute Sangsang, Binbin will come with a donkey after travelling ? meters and finding ? LOVE strings at last.”
Of cause, the travel distance should be as short as possible, and at the same time the “LOVE” string should be as long as possible.
Sample Input
2
4 4
1 2 1 L
2 1 1 O
1 3 1 V
3 4 1 E
4 4
1 2 1 L
2 3 1 O
3 4 1 V
4 1 1 E
Sample Output
Case 1: Cute Sangsang, Binbin will come with a donkey after travelling 4 meters and finding 1 LOVE strings at last.
Case 2: Binbin you disappoint Sangsang again, damn it!
题目大意:BB要骑着他的小毛驴去找SS,这是一只很奇葩的驴,它走路的时候,会画出“LOVE”。现在给你n个点,给你m条路,每条路包括起点终点以及长度和驴在这条路上会画出的字母。问,在画出完整的“LOVE”的前提下,从BB家点1,到SS家点n的最短路,以及画出的完整的“LOVE”的个数。“LOVE”至少要画完整的一个,否则BB就要被甩了。
解题思路:SPFA。在原先的d数组上加四个状态“L”,“O”,“V”,“E“,判断条件改为 d[u][letter] + edges[i].dis < d[v][next__letter],并用一个二维cnt数组记录当前状态所画的最多的字母数,当d[u][letter] + edges[i].dis == d[v][next__letter]时比较cnt[v][next__letter]和__cnt[u][letter] + 1,维护cnt数组。还有一个要注意的地方,如果SS就在BB家,这种情况要注意特判。
SS就在BB家
1 4
1 1 1 L
1 1 1 O
1 1 1 V
1 1 1 E
年轻人就是喜欢没事找事
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <cmath>
#include <cstdlib>
#include <queue>
using namespace std;
typedef long long ll;
const int N = 2400;
const int M = 24000;
const ll INF = 1e15;
int n, m, s, t;
int vis[N];
ll d[N][5];
int en;
int head[M];
struct node {
int to, next, let;
ll dis;
}edge[M];
void addEdge(int u,int v,ll x, int f) {
edge[en].to = v;
edge[en].next = head[u];
edge[en].dis = x;
edge[en].let = f;
head[u] = en++;
edge[en].to = u;
edge[en].next = head[v];
edge[en].dis = x;
edge[en].let = f;
head[v] = en++;
}
int Cnt[N][4];
void SPFA() {
queue<int> Q;
for(int i = 1; i <= n; i++) {
for (int j = 0; j <= 4; j++) {
d[i][j] = INF;
Cnt[i][j] = 0;
}
vis[i] = 0;
}
d[s][0] = 0;
vis[s] = 1;
Q.push(s);
while(!Q.empty()) {
int u = Q.front();
Q.pop();
vis[u] = 0;
int flag = 0;
for(int i = head[u]; i != -1; i = edge[i].next) {
int v = edge[i].to;
int f = edge[i].let;
int next = (f + 1) % 4;
if(d[u][f] + edge[i].dis < d[v][next]) {
d[v][next] = d[u][f] + edge[i].dis;
Cnt[v][next] = Cnt[u][f] + 1;
if(!vis[v]) {
Q.push(v);
vis[v] = 1;
}
} else if (d[u][f] + edge[i].dis == d[v][next]) {
if (Cnt[u][f] + 1 > Cnt[v][next]) {
Cnt[v][next] = Cnt[u][f] + 1;
}
}
}
}
}
ll check[5], sum;
int input() {
sum = 0;
memset(check, 0, sizeof(check));
int u, v;
ll c;
char l;
int cnt = 0;
for (int i = 0; i < m; i++) {
scanf("%d %d %lld %c", &u, &v, &c, &l);
int flag;
if (l == ‘L‘) flag = 0;
else if (l == ‘O‘) flag = 1;
else if (l == ‘V‘) flag = 2;
else if (l == ‘E‘) flag = 3;
addEdge(u, v, c, flag);
if (u == 1 && v == 1 && n == 1) {
if (!check[flag]) {
cnt++;
check[flag] = c;
} else {
check[flag] = min(check[flag], c);
}
}
}
return cnt;
}
int main() {
int T, Case = 1;
scanf("%d", &T);
while (T--) {
en = 0;
memset(head, -1, sizeof(head));
printf("Case %d: ", Case++);
scanf("%d %d", &n, &m);
s = 1, t = n;
int temp = input();
if (temp == 4) {
sum = check[0] + check[1] + check[2] + check[3];
printf("Cute Sangsang, Binbin will come with a donkey after travelling %lld meters and finding 1 LOVE strings at last.\n", sum);
continue;
}
SPFA();
if (!Cnt[n][0] || d[n][0] == INF) {
printf("Binbin you disappoint Sangsang again, damn it!\n");
} else {
printf("Cute Sangsang, Binbin will come with a donkey after travelling %lld meters and finding %d LOVE strings at last.\n", d[n][0], Cnt[n][0] / 4);
}
}
return 0;
}
版权声明:本文为博主原创文章,未经博主允许不得转载。