其他分享
首页 > 其他分享> > Codeforces Round #442 (Div. 2)--D. Olya and Energy Drinks--BFS+剪枝

Codeforces Round #442 (Div. 2)--D. Olya and Energy Drinks--BFS+剪枝

作者:互联网

D. Olya and Energy Drinks

time limit per test

2 seconds

memory limit per test

256 megabytes

input

standard input

output

standard output

Olya loves energy drinks. She loves them so much that her room is full of empty cans from energy drinks.

Formally, her room can be represented as a field of n × m cells, each cell of which is empty or littered with cans.

Olya drank a lot of energy drink, so now she can run k meters per second. Each second she chooses one of the four directions (up, down, left or right) and runs from 1 to k meters in this direction. Of course, she can only run through empty cells.

Now Olya needs to get from cell (x1, y1) to cell (x2, y2). How many seconds will it take her if she moves optimally?

It's guaranteed that cells (x1, y1) and (x2, y2) are empty. These cells can coincide.

Input

The first line contains three integers nm and k (1 ≤ n, m, k ≤ 1000) — the sizes of the room and Olya's speed.

Then n lines follow containing m characters each, the i-th of them contains on j-th position "#", if the cell (i, j) is littered with cans, and "." otherwise.

The last line contains four integers x1, y1, x2, y2 (1 ≤ x1, x2 ≤ n, 1 ≤ y1, y2 ≤ m) — the coordinates of the first and the last cells.

Output

Print a single integer — the minimum time it will take Olya to get from (x1, y1) to (x2, y2).

If it's impossible to get from (x1, y1) to (x2, y2), print -1.

Examples

input

Copy

3 4 4
....
###.
....
1 1 3 1

output

Copy

3

input

Copy

3 4 1
....
###.
....
1 1 3 1

output

Copy

8

input

Copy

2 2 1
.#
#.
1 1 2 2

output

Copy

-1

Note

In the first sample Olya should run 3 meters to the right in the first second, 2 meters down in the second second and 3 meters to the left in the third second.

In second sample Olya should run to the right for 3 seconds, then down for 2 seconds and then to the left for 3 seconds.

Olya does not recommend drinking energy drinks and generally believes that this is bad.

 

求起点到终点的最小步数,一次可以向一个方向走1-k步,求最小步数。

BFS是肯定的,四个方向内再套一个1-k的循环,让它向四个方向走。然后考虑剪枝,不剪枝就超时了。

当他走一个方向时,到达了x,y点,如果说dis[x][y]<step,那么这个方向就不用再继续搜了。

 

#include <algorithm>    //STL通用算法
#include <bitset>     //STL位集容器
#include <cmath>
#include <cstdio>
#include <cstring>
#include <deque>      //STL双端队列容器
#include <exception>    //异常处理类
#include <fstream>
#include <functional>   //STL定义运算函数(代替运算符)
#include <limits>
#include <list>      //STL线性列表容器
#include <map>       //STL 映射容器
#include <iomanip>
#include <ios>      //基本输入/输出支持
#include<iosfwd>     //输入/输出系统使用的前置声明
#include <iostream>
#include <istream>     //基本输入流
#include <ostream>     //基本输出流
#include <queue>      //STL队列容器
#include <set>       //STL 集合容器
#include <sstream>    //基于字符串的流
#include <stack>      //STL堆栈容器    
#include <string>     //字符串类
#include <vector>     //STL动态数组容器
#define ll long long
using namespace std;
#define rep(i,a,b) for(register int i=(a);i<=(b);i++)
#define dep(i,a,b) for(register int i=(a);i>=(b);i--)
//priority_queue<int,vector<int>,less<int> >q;
int dx[]= {-1,1,0,0,-1,-1,1,1};
int dy[]= {0,0,-1,1,-1,1,1,-1};
const int maxn = 1000+66;
const int maxm=100000+66;
const ll mod=1e9+7;
const ll inf=0x3f3f3f3f3f3f3f3fLL;
const int INF=99999999;
int n,m,k;
int bx,by,ex,ey;
char ch[maxn][maxn];
int dis[maxn][maxn];
bool vis[maxn][maxn];
struct node
{
    int x;
    int y;
    int step;
};
int bfs()
{
    rep(i,1,n)
    {
        rep(j,1,m)
        {
            dis[i][j]=INF;
        }
    }
    queue<node>q;
    q.push(node{bx,by,0});
    vis[bx][by]=1;
    dis[bx][by]=0;
    node cur;
    while(q.size())
    {
        cur=q.front();
        q.pop();
        rep(i,0,3)
        {
            rep(j,1,k)
            {
                int x=cur.x+j*dx[i];
                int y=cur.y+j*dy[i];
                int step=cur.step+1;
                if(ch[x][y]=='#'||x<1||x>n||y<1||y>m||(vis[x][y]&&step>dis[x][y]))
                    break;//这个方向不用再往下走了,也就是加一个剪枝
                //若当前方向的点被访问过,并且起点到xy的距离大于当前点的距离,不再搜索此方向
                if(vis[x][y])
                    continue;//如果已经走过或步数大于已经存在的点
                vis[x][y]=1;
                dis[x][y]=step;
                q.push(node{x,y,step});
            }
        }
    }
    return dis[ex][ey]==INF?-1:dis[ex][ey];
}
int main()
{
    while(scanf("%d %d %d",&n,&m,&k)!=EOF)
    {
        rep(i,1,n)
        {
            scanf("%s",ch[i]+1);
        }
        scanf("%d %d %d %d",&bx,&by,&ex,&ey);
        printf("%d\n",bfs());
    }
}

 

标签:剪枝,int,442,Energy,Olya,STL,second,include,dis
来源: https://blog.csdn.net/lanshan1111/article/details/100526023