HDU 2416 POJ 3346 Treasure of the Chimp Island(最短路)

来源:互联网 发布:域名的商业价值 编辑:程序博客网 时间:2024/06/05 15:24

题意:问能否从城外进入城堡,并取得宝藏。求取得宝藏所需的最短时间。。

1,边界有字母,或者#表示入口。#表示从这里进入可以获得0个炸弹,A表示可以获得1个炸弹,B两个。。。

2, 星号表示障碍,不可通过。点表示同路,通过的时间为0。1-9表示从这点通过需要话费的时间,当然这个点可以用炸弹掉,通过的时间为0。


开始的时候我按照普通的做法,在边界上找到一个入口就搜一次,结果TLE,

然后换成从宝藏开始往外搜,WA,

最后看了一下题,发现题中有说明,一次只能带一次炸药,即只能从边界直接往里走,不能边界走向边界。加了这个条件之后就AC了。

#include <iostream>#include <cstdio>#include <cstring>#include <algorithm>#include <cmath>#include <queue>using namespace std;const int N = 109;const int INF =0x3f3f3f3f;int n,m;int dp[N][N][30];bool visit[N][N][30];char map[N][N];bool init(){    n=0;    while(1)    {        gets(map[n]);        if(map[n][0]=='-') return false;        if(strlen(map[n])==0) break;        n++;    }    m = strlen(map[0]);    return true;}int dx[]={0,0,-1,1};int dy[]={-1,1,0,0};struct nod{    int dis;    int x,y,dep;    bool operator <(const nod t) const    {        return dis>t.dis;    }};priority_queue<nod> que;bool oor(int x,int y){    if(x<0||x>=n) return false;    if(y<0||y>=m) return false;    return true;}void deal(){    memset(dp,INF,sizeof(dp));    memset(visit,false,sizeof(visit));    int enx,eny;    for(int i=0;i<n;i++)    for(int j=0;j<m;j++)    if(map[i][j]=='$')    {        enx=i,eny=j;    }    while(!que.empty()) que.pop();    nod e,t;    e.dep=0;e.dis=0;e.x=enx,e.y=eny;    que.push(e);    while(!que.empty())    {        e = que.top(); que.pop();        if(visit[e.x][e.y][e.dep]) continue;        visit[e.x][e.y][e.dep] = true;        dp[e.x][e.y][e.dep] = e.dis;        if(e.x==0||e.y==0||e.x==n-1||e.y==m-1) continue;        for(int i=0;i<4;i++)        {            int tx=e.x+dx[i],ty=e.y+dy[i];            if(!oor(tx,ty)||map[tx][ty]=='*') continue;            if(map[tx][ty]>='0'&&map[tx][ty]<='9')            {                t.dis = e.dis+map[tx][ty]-'0';                t.dep = e.dep;                t.x = tx,t.y = ty;                if(!visit[tx][ty][t.dep]&&dp[tx][ty][t.dep]>t.dis)                que.push(t);                t.dis = e.dis;                t.dep = e.dep+1;                t.x = tx,t.y = ty;                if(!visit[tx][ty][t.dep]&&dp[tx][ty][t.dep]>t.dis&&t.dep<=26)                que.push(t);            }            else            {                t.dis = e.dis;                t.dep = e.dep;                t.x = tx,t.y = ty;                if(dp[tx][ty][t.dep]>t.dis)                que.push(t);            }        }    }}int fin(int x,int y){    int ans = INF;    int d = map[x][y]=='#'?0:map[x][y]-'A'+1;    for(int i=0;i<=d;i++)    ans=min(dp[x][y][d],ans);    return ans;}void solve(){    deal();    int ans=INF;    for(int i=1;i<n;i++)    {        if(map[i][0]!='*')        ans=min(fin(i,0),ans);        if(map[i][m-1]!='*')        ans=min(fin(i,m-1),ans);    }    for(int i=1;i<m;i++)    {        if(map[0][i]!='*')        ans=min(fin(0,i),ans);        if(map[n-1][i]!='*')        ans=min(fin(n-1,i),ans);    }    if(ans==INF) printf("IMPOSSIBLE\n");    else printf("%d\n",ans);}int main(){    freopen("in.txt","r",stdin);    while(1)    {        if(!init()) break;        solve();    }    return 0;}


原创粉丝点击