DFS&BFS專題(一)

題目列表
1.POJ-1321(簡單DFS)
2.POJ-2251(三維座標BFS)
3.POJ-1426(DFSf構造)
4.POJ-3087(BFS模擬)
5.POJ-3414(BFS模擬+記錄路徑)
6.UVA-11624(兩次BFS)
7.POJ-3984(簡單DFS&BFS都可以,記錄路徑)
8.HDU-1241(DFS種子填充)
9.HDU-1495(BFS求最短路)
10.HDU - 2612 (兩次BFS)

Q1:POJ - 1321
題意:中文題
思路:
DFS的參數是從第i行往下搜索,設置num表示目前已經放好的棋子,如果num==k,放置的種數加1,如果遞歸層數大於n直接返回結束遞歸

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
int n, k;
char Map[10][10];
int v[10];
int sum, num;
void dfs(int x)
{
    if(num == k){sum++; return;}
    if(x > n)return;
    for(int i = 0; i < n; i++)
        if(Map[x][i] == '#' && !v[i])
        {
            v[i] = 1;
            num ++;
            dfs(x + 1);
            num--;
            v[i] = 0;
        }
    dfs(x + 1);
}
int main()
{
    while(cin >> n >> k)
    {
        memset(Map, 0, sizeof(Map));
        if(n == -1 && k == -1)break;
        for(int i = 0; i < n; i++)cin >> Map[i];
        memset(v, 0, sizeof(v));
        sum = num =0;
        dfs(0);
        cout<<sum<<endl;
    }
}

Q2:POJ-2251
題意:
在一個立體空間, 輸入三個數,L,R,C,代表有L個平面,R行,C列,.代表可以走,#代表不能走,S代表開始點,E代表結束點,問從S開始走,對每個位置,有六個走法,即空間的六個方向的走法(上下東南西北),一分鐘可以走一個點,問從S走到E點,最少可以經過多少分鐘,若不能到達,則輸出Trapped!
思路:
簡單BFS運用,只是把普通的二維平面變成了三維立體,由四個方向變成了六個方向

#include<iostream>
#include<queue>
#include<cstring>
using namespace std;
char Map[30][30][30];
int visit[30][30][30];
int dir[6][3]={1,0,0,-1,0,0,0,1,0,0,-1,0,0,0,1,0,0,-1};
struct node
{
    int l,x,y,s;
    node(int ll,int xx,int yy,int ss):l(ll),x(xx),y(yy),s(ss){}
};
int main()
{
    int l,x,y;
    int s1,s2,s3,c1,c2,c3;
    while(cin>>l>>x>>y)
    {
        if(!l&&!x&&!y)break;
        memset(visit,0,sizeof(visit));
        memset(Map,0,sizeof(Map));
        for(int i=0;i<l;i++)
        {
            for(int j=0;j<x;j++)cin>>Map[i][j];
        }
        for(int i=0;i<l;i++)
            for(int j=0;j<x;j++)
                for(int k=0;k<y;k++)
        {
            if(Map[i][j][k]=='S')
            {
                s1=i;s2=j;s3=k;
            }
            if(Map[i][j][k]=='E')
            {
                c1=i;c2=j;c3=k;
            }
        }
        queue<node>q;
        q.push(node(s1,s2,s3,0));
        visit[s1][s2][s3]=1;
        for(;;)
        {
            if(q.empty())
            {
                cout<<"Trapped!"<<endl;
                break;
            }
            node a=q.front();
            //cout<<a.l<<" "<<a.x<<" "<<a.y<<endl;
            if(a.l==c1&&a.x==c2&&a.y==c3)
            {
                cout<<"Escaped in "<<a.s<<" minute(s)."<<endl;
                break;
            }
            for(int i=0;i<6;i++)
            {
                int cnt1=a.l+dir[i][0];
                int cnt2=a.x+dir[i][1];
                int cnt3=a.y+dir[i][2];
                if(cnt1>=0&&cnt1<l&&cnt2>=0&&cnt2<x&&cnt3>=0&&cnt3<y&&!visit[cnt1][cnt2][cnt3]&&Map[cnt1][cnt2][cnt3]!='#')
                {
                    visit[cnt1][cnt2][cnt3]=1;
                    q.push(node(cnt1,cnt2,cnt3,a.s+1));
                }
            }
            q.pop();
        }
   }
   return 0;
}

Q3:POJ-1426
題意:
給你一個[1,200]之間的整數n,要你求它的一個非0倍數m,這個m的十進制數只包含0和1.m不超過100位.
思路:
由於本題的數只有0和1構成,自然就想到了自己構造這個符合要求的數。所以這裏我用DFS來構造這個數。雖然本題說最終結果數<=100位,但是經過測試本題測試數據中需要構造的數在unsigned long long 範圍內有解,所以下面我用unsigned long long來表示需要構造的數。(並沒有用高精度大整數)
DFS構造過程很簡單了,就是每層循環向個位添加一個0或1即可。但是記得如果找到了一個合法的數要及時退出所有DFS遞歸函數。

#include<iostream>
#include<cstdio>
using namespace std;
typedef unsigned __int64 ll;
bool s;
void dfs(ll x,int n,int k)
{
    if(s)return;
    if(x%n==0)
    {
        printf("%I64u\n",x);
        s=true;
        return ;
    }
    if(k==19)return;
    dfs(x*10,n,k+1);
    dfs(x*10+1,n,k+1);
}
int main()
{
    int n;
    while(cin>>n)
    {
        if(!n)break;
        s=false;
        dfs(1,n,0);
    }
    return 0;
}

Q4:POJ-3087
題意:
給定長度都爲C兩個字符串,S1,S2,和一個要求的結果字符串S12。先把 S2 的最下面一張牌放在最下面,然後S1,S2交錯的疊放,得到新的S12,再把S12最下面的C個字符賦值給S1,把剩下的賦值給S2,再次重複上面的過程。最後求出要得到目標字符串S,問最少需要幾步。
思路:
直接BFS模擬,將下一步可得的結果放入隊列中(題目所給出的輸入是從低向上排列的。)

#include<string>
#include<iostream>
#include<queue>
#include<map>
using namespace std;
int n;
map<string,int>ant;
string answer;
string f(string s1,string s2)
{
    string s12;
    for(int i=0;i<n;i++)
    {
        s12+=s2[i];
        s12+=s1[i];
    }
    return s12;
}

int bfs(string s1,string s2)
{
    ant.clear();
    string s12=f(s1,s2);
    ant[s12]=1;
    queue<string>q;
    q.push(s12);
    while(!q.empty())
    {
        string s=q.front();
        s1.clear();
        s2.clear();
        q.pop();
        if(s==answer)return ant[s];
        for(int i=0;i<n;i++)s1+=s[i];
        for(int i=n;i<2*n;i++)s2+=s[i];
        s12=f(s1,s2);
        if(ant.find(s12)!=ant.end())return -1;
        ant[s12]=ant[s]+1;
        q.push(s12);
    }
    return -1;
}
int main()
{
    int k;
    cin>>k;
    for(int i=1;i<=k;i++)
    {
        cin>>n;
        string s1,s2;
        cin>>s1>>s2;
        cin>>answer;
        cout<<i<<" "<<bfs(s1,s2)<<endl;
    }
    return 0;
}

Q5:POJ-3414
題意:
給你兩個容器 A B 問是否能夠經過有限的步驟倒水,得到容量爲 C 的水
輸出最小的步數,同時輸出每一步的操作。
如果不能達到目標狀態,則輸出 impossible
思路:
總狀態只有那麼多, 反正每一步後都只有 6 種操作明顯的 BFS 關鍵是每一步路徑的記錄。
開始用 BFS + 容器做了一遍,發現還是無法處理好輸出路徑問題,只好重新開始用數組模擬。
容器雖然很好用又方便,但是在不考慮內存的狀況下,效率終究比不上數組模擬的了。

注意到 A 和 B 的範圍是 1 到 100 的整數,
那麼我們可以用vis[i][j]來記錄每一種狀態 0 <= i, j <= 100 ;
i 表示目前 A 容器中的水, j 表示目前 B 容器中的水

應該很容易就能分析出,對應於每一種狀態的下一步只有六種情況:

一:用水池中的水裝滿 A
二:用水池中的水裝滿 B
三:把 A 中的水全部倒進廢水池
四:把 B 中的水全部倒進廢水池
五:把 A 中的水倒進 B 【不能溢出】
那麼對應可能會有兩種狀態:用 k1 表示 A 中的水, k2 表示 B 中的水
如果 k1+k2 <= B 則 k2 = k1+k2; k1 = 0 【不能夠裝滿容器 B】注意順序
否則 k1 = k1+k2-B; k2 = B 【能夠裝滿容器 B】
六:把 B 中的水倒進 A 【不能溢出】
也有兩種情況,分析同上
如果 k1+k2 <= A 則 k1 = k1+k2; k2 = 0;
否則 k2 = k1+k2-A; k1 = A

用結構體數組來模擬隊列
用 k1,k2 來記錄當前容器中水的狀態
前面已經分析過對應於每種情況只有 6 種操作, 那麼對應每種情況的操作記錄爲 1 到 6 輸出時處理下就好了。
當然少不了記錄到當前狀態最少用了多少步數 step
因爲要記錄路徑,所以定義一個 f 來記錄上一步在數組模擬隊列中的下標。

最後如果能夠達到目的,在判定最後一步的時候記錄下最後一步在數組中的編號 lastIndex
然後從lastIndex從後往前找【f】前一個步驟在數組中的編號存在 id[] 中
最後再按照掃描出的路徑依次遍歷即可。

#include<iostream>
#include<cstring>
#include<queue>
#include<string>
using namespace std;

struct node
{
    int a,b,f,step;///a爲第一個瓶子得水量,b爲第二個,f爲上一步的下標,step表示步數
    string s;
}pot[100000];
int visit[110][110];
int x,y,ans;
string cnt[10000];
void bfs()
{
    int head = 0, tail = 1;
    pot[0].a = pot[0].b = pot[0].step = 0;
    pot[0].f = -1;
    visit[0][0] = 1;
    while(head != tail)
    {
        if(pot[head].a == ans || pot[head].b == ans)
        {
            cout<<pot[head].step<<endl;
            int i = -1;
            while(pot[head].f != -1)
            {
                cnt[++i] = pot[head].s;
                head = pot[head].f;
            }
            for(;i >= 0;i--)cout<<cnt[i]<<endl;
            return;
        }
        if(pot[head].a < x)
        {
            node c;
            c.a = x;
            c.b = pot[head].b;
            c.f = head;
            c.step = pot[head].step + 1;
            c.s = "FILL(1)";
            if(!visit[c.a][c.b])
            {
                pot[tail++] = c;
                visit[c.a][c.b] = 1;
            }
        }
        if(pot[head].b < y)
        {
            node c;
            c.a = pot[head].a;
            c.b = y;
            c.f = head;
            c.step = pot[head].step + 1;
            c.s = "FILL(2)";
            if(!visit[c.a][c.b])
            {
                pot[tail++] = c;
                visit[c.a][c.b] = 1;
            }
        }
        if(pot[head].a)
        {
            node c;
            c.a = 0;
            c.b = pot[head].b;
            c.f = head;
            c.step = pot[head].step + 1;
            c.s = "DROP(1)";
            if(!visit[c.a][c.b])
            {
                pot[tail++] = c;
                visit[c.a][c.b] = 1;
            }
        }
        if(pot[head].b)
        {
            node c;
            c.a = pot[head].a;
            c.b = 0;
            c.f = head;
            c.step = pot[head].step + 1;
            c.s = "DROP(2)";
            if(!visit[c.a][c.b])
            {
                pot[tail++] = c;
                visit[c.a][c.b] = 1;
            }
        }
        if(pot[head].a + pot[head].b <= y)
        {
            node c;
            c.a = 0;
            c.b = pot[head].a + pot[head].b;
            c.f = head;
            c.step = pot[head].step + 1;
            c.s = "POUR(1,2)";
            if(!visit[c.a][c.b])
            {
                pot[tail++] = c;
                visit[c.a][c.b] = 1;
            }
        }
        if(pot[head].a + pot[head].b > y)
        {
            node c;
            c.a = pot[head].a + pot[head].b - y;
            c.b = y;
            c.f = head;
            c.step = pot[head].step + 1;
            c.s = "POUR(1,2)";
            if(!visit[c.a][c.b])
            {
                pot[tail++] = c;
                visit[c.a][c.b] = 1;
            }
        }
        if(pot[head].a + pot[head].b <= x)
        {
            node c;
            c.a = pot[head].a + pot[head].b;
            c.b = 0;
            c.f = head;
            c.step = pot[head].step + 1;
            c.s = "POUR(2,1)";
            if(!visit[c.a][c.b])
            {
                pot[tail++] = c;
                visit[c.a][c.b] = 1;
            }
        }
        if(pot[head].a + pot[head].b > x)
        {
            node c;
            c.a = x;
            c.b = pot[head].a + pot[head].b - x;
            c.f = head;
            c.step = pot[head].step + 1;
            c.s = "POUR(2,1)";
            if(!visit[c.a][c.b])
            {
                pot[tail++] = c;
                visit[c.a][c.b] = 1;
            }
        }
        head++;
    }
    cout<<"impossible"<<endl;
}
int main()
{
    while(cin >> x >> y >> ans)
    {
        memset(visit, 0, sizeof(visit));
        if(ans > x && ans > y)
        {
            cout<<"impossible"<<endl;
            continue;
        }
        bfs();
    }
}

Q6:UVA-11624
題意:
在一個矩形方陣裏面,一個人要從一個位置走向另一個位置,其中某些地方有火源,每過一分鐘,火源就會點燃相鄰的點,同時相鄰的點也變成了火源。人不能通過有火的點。問一個人能夠安全地走到目的地去?最短時間多少?
思路:
Joe的起點唯一,但是起火的地方並不是唯一的,這是我們首先要明確的。
關鍵是之後應該怎樣處理火勢的蔓延與Joe逃跑這兩個過程的關係,我們要清楚:只有火勢可以影響Joe的逃跑路線,但Joe的逃跑路線絕對不能影響火勢,所以這兩個過程不可能出現在同一個BFS中。
可以這樣想:既然火勢的蔓延時不隨人的主觀意願而改變的,那麼我們可以先讓火勢肆意蔓延,看它到底能燒到哪裏,以及燒到某個地方所需要的時間,這樣,主人公在逃跑的過程中,只要在火勢到達之前趕到某個地方就可以了。
綜上,需要兩個BFS,第一個計算火勢蔓延到任意一點所需要的時間,如果火勢永遠到達不了某些點,就把這些點的時間設爲正無窮,之後再搜索Joe的逃跑路線,條件要增加時間這一項,只要Joe能到達迷宮的邊界,就算逃出來了。

#include<iostream>
#include<cstring>
#include<cstdio>
#include<queue>
#include<algorithm>
using namespace std;
char Map[1010][1010];
bool v[1010][1010];
int ans[1010][1010];
int dir[4][2] = {1,0,0,1,-1,0,0,-1};
struct Node
{
    int x, y, step;
    Node(int xx, int yy, int ss):x(xx),y(yy),step(ss){}
};
int n, m, x0, y0;
queue<Node>q;
bool judge(int x, int y)
{
    return (x >= 0 && x < n && y >= 0 && y < m && !v[x][y]);
}

void bfs()
{
    for(int i = 0; i < n; i++)
    {
        for(int j = 0; j < m; j++)ans[i][j] = 1 << 30;
    }///有可能火到不了一些地方,先把ans設置成無窮大
    while(!q.empty())
    {
        Node a = q.front();
        q.pop();
        for(int i = 0; i < 4; i++)
        {
            int x = a.x + dir[i][0];
            int y = a.y + dir[i][1];
            if(judge(x, y) && Map[x][y] != '#')
            {
                v[x][y] = 1;
                q.push(Node(x, y, a.step + 1));
                ans[x][y] = a.step + 1;
            }
        }
    }
    memset(v, 0, sizeof(v));
    q.push(Node(x0, y0, 1));
    v[x0][y0] = 1;
    while(!q.empty())
    {
        Node a = q.front();
        q.pop();
        if(a.x == 0 || a.x == n - 1 || a.y == 0 || a.y == m - 1)
        {
            cout<<a.step<<endl;
            return ;
        }
        for(int i = 0; i < 4; i++)
        {
            int x = a.x + dir[i][0];
            int y = a.y + dir[i][1];
            if(judge(x, y) && Map[x][y] == '.' && a.step + 1 <= ans[x][y])
            {
                v[x][y] = 1;
                q.push(Node(x, y, a.step + 1));
            }
        }
    }
    cout<<"IMPOSSIBLE"<<endl;
}
int main()
{
    int T;
    cin >> T;
    while(T--)
    {
        while(!q.empty())q.pop();
        memset(Map, 0, sizeof(Map));
        memset(v, 0, sizeof(v));
        cin >> n >> m;
        for(int i = 0; i < n; i++)
        {
            cin >> Map[i];
            for(int j = 0; j < m; j++)
            {
                if(Map[i][j] == 'J')
                {
                    x0 = i;
                    y0 = j;
                }
                if(Map[i][j] == 'F')
                {
                    v[i][j] = 1;
                    q.push(Node(i, j, 0));
                }
            }
        }
        bfs();
        /*
        for(int i = 0; i < n; i++)
        {
            for(int j = 0; j < m; j++)
                cout<<ans[i][j]<< " ";
            cout<<endl;
        }*/
    }
    return 0;
}

Q7:POJ-3984
題意:
中文題
思路:
反正就是簡單的結構體套結構體存一下父節點就行,由於記錄路徑,這裏直接用數組代替隊列

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;

struct node
{
    int x,y,f;
}a[30];
int dir[4][2]={1,0,0,1,-1,0,0,-1};
int visit[6][6];
int lode[25][2];
int main()
{
    int Map[5][5];
    for(int i=0;i<5;i++)
        for(int j=0;j<5;j++)cin>>Map[i][j];
    a[0].x=a[0].y=0;a[0].f=-1;
    visit[0][0]=1;
    int head=0;int tail=1;
    while(head!=tail)
    {
        if(a[head].x==4&&a[head].y==4)
        {
            int i=0;
            while(a[head].f!=-1)
            {
                lode[i][0]=a[head].x;
                lode[i][1]=a[head].y;
                i++;
                head=a[head].f;
            }
            lode[i][0]=lode[i][1]=0;
            for(;i>=0;i--)
            {
                printf("(%d, %d)\n",lode[i][0],lode[i][1]);
            }
            break;
        }
        for(int i=0;i<4;i++)
        {
            int x=a[head].x+dir[i][0];
            int y=a[head].y+dir[i][1];
            if(x>=0&&x<5&&y>=0&&y<5&&!visit[x][y]&&Map[x][y]==0)
            {
                a[tail].x=x;
                a[tail].y=y;
                a[tail].f=head;
                visit[x][y]=1;
                tail++;
            }
        }
        head++;
    }
    return 0;
}

Q8:HDU-1241
題意:
就是給你一個地圖,找出所有不相連(八個方向)的@組合有多少個
思路:
先對整個地圖進行遍歷,找到一個入口,然後用DFS深搜,相連的@都找到,並且將其標記爲1,再找下一個入口,再DFS能夠到達的所有@標記爲2,最後的數字就是油田的數量。

#include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
char Map[110][110];
int dir[8][2]={0,1,1,0,0,-1,-1,0,1,1,1,-1,-1,1,-1,-1};
int m,n;
int visit[110][110];
int num;
void dfs(int i,int j)
{
    if(visit[i][j])return;
    visit[i][j]=num;
    for(int k=0;k<8;k++)
    {
        int x=i+dir[k][0];
        int y=j+dir[k][1];
        if(x>=0&&x<m&&y>=0&&y<n&&Map[x][y]=='@'&&!visit[x][y])dfs(x,y);
    }
}
int main()
{
    while(cin>>m>>n)
    {
        if(!m&&!n)break;
        memset(visit,0,sizeof(visit));
        memset(Map,0,sizeof(Map));
        getchar();
        for(int i=0;i<m;i++)
        {
            for(int j=0;j<n;j++)
            {
                cin>>Map[i][j];
            }
            getchar();
        }
        num=0;
        for(int i=0;i<m;i++)
        {
            for(int j=0;j<n;j++)
            if(Map[i][j]=='@'&&!visit[i][j])
            {
                num++;
                dfs(i,j);
            }
        }

        cout<<num<<endl;
    }return 0;
}

Q9:HDU - 1495

題意:
中文題
思路:
我們有明確的初始狀態(s=s,a=0,b=0)和終止狀態(s=s>>1,a=s>>1,b=0) (PS:a爲大號杯)
而每一步我們都有六個可選擇的方向(s->a ;s->b ; a->s ; a->b ;b->s ;b->a),我們要得到最少的倒的次數,當然就是bfs咯。

#include<iostream>
#include<cstring>
#include<queue>
using namespace std;
struct node
{
    int cnt[3],s;
};
int visit[110][110][110];
int b[3],half;
bool f(int x)
{
    if(x==half)return true;
    else return false;
}
void bfs()
{
    queue<node>q;
    node a;
    a.cnt[0]=b[0];
    a.cnt[1]=a.cnt[2]=a.s=0;
    visit[a.cnt[0]][a.cnt[1]][a.cnt[2]]=1;
    q.push(a);
    while(!q.empty())
    {
        a=q.front();
        q.pop();

        if(f(a.cnt[0])&&f(a.cnt[1])||f(a.cnt[0])&&f(a.cnt[2])||f(a.cnt[1])&&f(a.cnt[2]))
        {
            cout<<a.s<<endl;
            return ;
        }
        for(int i=0;i<3;i++)
        {
            if(a.cnt[i]>0)
            {
                for(int j=0;j<3;j++)
                {
                    node temp=a;
                    if(i==j)continue;
                    if(temp.cnt[i]+temp.cnt[j]>=b[j])
                    {
                        temp.cnt[i]+=temp.cnt[j]-b[j];
                        temp.cnt[j]=b[j];
                    }
                    else
                    {
                        temp.cnt[j]+=temp.cnt[i];
                        temp.cnt[i]=0;
                    }
                    if(!visit[temp.cnt[0]][temp.cnt[1]][temp.cnt[2]])
                    {
                        temp.s++;
                        q.push(temp);
                        visit[temp.cnt[0]][temp.cnt[1]][temp.cnt[2]]=1;
                    }
                }
            }
        }
    }
    cout<<"NO"<<endl;
}
int main()
{
    while(cin>>b[0]>>b[1]>>b[2])
    {
        memset(visit,0,sizeof(visit));
        if(b[0]+b[1]+b[2]==0)break;
        if(b[0]%2!=0)
        {
            cout<<"NO"<<endl;
            continue;
        }
        else
        {
            half=b[0]/2;
            bfs();
        }
    }
    return 0;
}

Q10:HDU - 2612
題意:
Y和M要在KFC約會,地圖上有多個KFC,求在哪個KFC兩人所走總距離最短,(注意KFC可以當做路)
思路:
用2次BFS,分別求出2個點到各個KFC的最短距離,然後找出和最小的即可

#include<iostream>
#include<cstring>
#include<queue>
#include<cstdio>
#include<algorithm>
using namespace std;
char Map[210][210];
int visit[210][210];
int sum1[210][210],sum2[210][210];
int dir[4][2]={1,0,0,1,-1,0,0,-1};
int m,n;
struct node
{
    int x,y,s;
    node(int xx,int yy,int ss):x(xx),y(yy),s(ss){}
};
int main()
{
    while(cin>>m>>n)
    {
        int x1,y1,x2,y2,p[5];
        memset(sum1,0,sizeof(sum1));
        memset(sum2,0,sizeof(sum2));
        memset(Map,0,sizeof(Map));
        getchar();
        for(int i=0;i<m;i++)
        {
            for(int j=0;j<n;j++)
            {
                cin>>Map[i][j];
                if(Map[i][j]=='Y')
                {
                    p[1]=i;p[2]=j;
                }
                if(Map[i][j]=='M')
                {
                    p[3]=i;p[4]=j;
                }

            }  getchar();
        }
        queue<node>q;
        memset(visit,0,sizeof(visit));
        q.push(node(p[1],p[2],0));
        visit[p[1]][p[2]]=1;
        while(!q.empty())
        {
            node a=q.front();
            for(int j=0;j<4;j++)
                {
                    int x=a.x+dir[j][0];
                    int y=a.y+dir[j][1];
                    if(x>=0&&x<m&&y>=0&&y<n&&!visit[x][y]&&Map[x][y]!='#')
                    {
                        visit[x][y]=1;
                        q.push(node(x,y,a.s+1));
                        sum1[x][y]=a.s+1;
                    }
                }
                q.pop();
        }
        memset(visit,0,sizeof(visit));
        q.push(node(p[3],p[4],0));
        visit[p[3]][p[4]]=1;
        while(!q.empty())
        {
            node a=q.front();
            for(int j=0;j<4;j++)
                {
                    int x=a.x+dir[j][0];
                    int y=a.y+dir[j][1];
                    if(x>=0&&x<m&&y>=0&&y<n&&!visit[x][y]&&Map[x][y]!='#')
                    {
                        visit[x][y]=1;
                        q.push(node(x,y,a.s+1));
                        sum2[x][y]=a.s+1;
                    }
                }
                q.pop();
        }
        int minx=1<<30;
        for(int i=0;i<m;i++)
        {
            for(int j=0;j<n;j++)
            {
                if(Map[i][j]=='@'&&sum1[i][j]&&sum2[i][j])minx=min(minx,sum1[i][j]+sum2[i][j]);
            }
        }
        cout<<minx*11<<endl;
    }
    return 0;
}
發佈了40 篇原創文章 · 獲贊 35 · 訪問量 1萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章