這題看起來很屌。
但是實際上走到每個點(diǎn)之后,速度必然是當(dāng)前點(diǎn)和左上角點(diǎn)的差值的倒數(shù)。
所以,每個點(diǎn)到其他點(diǎn)的所花費(fèi)的時間都是這個點(diǎn)自己的值決定的。
而且沒可能經(jīng)過一個點(diǎn)兩次的,因為經(jīng)過兩次肯定是浪費(fèi)時間的。
問題就變成了求最短路徑。
注意:
這題的精度很莫名其妙,用C++可以AC的,G++、GCC都是WA。
不能用整數(shù)來保存時間,雖然看上去位數(shù)是夠用的,但是遇到比較屌的數(shù)據(jù)就掛了。
就在這個問題上杯具了很久。
#include <stdio.h>
#include <math.h>

#ifndef _countof
#define _countof(x) (sizeof(x)/sizeof(x[0]))
#endif

#define SIZE 128

int map[SIZE][SIZE], R, C, V;
double D[SIZE][SIZE], _tbl[128], *tbl = &_tbl[64];
int queue[65536][2], head, tail;
int vis[SIZE][SIZE];

inline void push(int y, int x, double d)


{
if (y < 0 || y >= R || x < 0 || x >= C)
return ;
if (d > D[y][x])
return ;
D[y][x] = d;
if (vis[y][x])
return ;
vis[y][x] = 1;
queue[tail][0] = y;
queue[tail][1] = x;
tail++;
tail &= _countof(queue) - 1;
}

inline void pop(int *y, int *x)


{
*y = queue[head][0];
*x = queue[head][1];
head++;
head &= _countof(queue) - 1;
vis[*y][*x] = 0;
}

int main()


{
int i, j;
double d;

freopen("e:\\test\\in.txt", "r", stdin);

for (i = -64; i <= 64; i++)
tbl[i] = pow(2.0, i);

scanf("%d%d%d", &V, &R, &C);

for (i = 0; i < R; i++)
{

for (j = 0; j < C; j++)
{
scanf("%d", &map[i][j]);
if (i || j)
map[i][j] -= map[0][0];
D[i][j] = 1e80;
}
}
map[0][0] = 0;

push(0, 0, 0);

while (head != tail)
{
pop(&i, &j);
d = D[i][j] + tbl[map[i][j]];
push(i + 1, j, d);
push(i - 1, j, d);
push(i, j + 1, d);
push(i, j - 1, d);
}

printf("%.2lf\n", D[R - 1][C - 1] / V);
return 0;
}
