//---------------------------------------------------------------
#include <bits/stdc++.h>
using namespace std;
#include <iostream>
#include <vector>
#include <cstdlib>
#include <cmath>
#include <math.h>
#include <sstream>
#include <numeric>
#include <cctype>
#include <bitset>
#include <cassert>
#include<algorithm>
//---------------------------------------------------------------
#define rep(i, n) for (int i = 0; i < (int)(n); i++)
#define rep1(i, n) for (int i = 1; i <= (int)(n); i++)
#define rep2(i, s, n) for (int i = (s); i < (int)(n); i++)
#define SIZE 100005
#define INF 1e18
#define all(x) x.begin(),x.end()
#define fi first
#define se second
#define vec vector
using pint = pair<int,int>;
using ll = long long;
using vll = vector<ll>;
using vvll = vector<vector<ll>>;
//---------------------------------------------------------------
template<class T> inline bool chmin(T& a, T b) { if (a > b) { a = b; return true; } return false; }
template<class T> inline bool chmax(T& a, T b) { if (a < b) { a = b; return true; } return false; }

const double pi = acos(-1);
const int mod = 1000000007;
struct mint {
    int64_t x;
    mint(int64_t x=0):x((x%mod+mod)%mod){}
    mint operator-() const { return mint(-x);}
    mint& operator+=(const mint a) {if ((x += a.x) >= mod) x -= mod;return *this;}
    mint& operator-=(const mint a) {if ((x += mod-a.x) >= mod) x -= mod;return *this;}
    mint& operator*=(const mint a) { (x *= a.x) %= mod; return *this;}
    mint operator+(const mint a) const { return mint(*this) += a;}
    mint operator-(const mint a) const { return mint(*this) -= a;}
    mint operator*(const mint a) const { return mint(*this) *= a;}
    mint pow(int64_t t) const {if (!t) return 1;mint a = pow(t>>1);a *= a;if (t&1) a *= *this;return a;}
    mint inv() const { return pow(mod-2);}
    mint& operator/=(const mint a) { return *this *= a.inv();}
    mint operator/(const mint a) {return mint(*this) /= a;}
};
istream& operator>>(istream& is, mint& a) { return is >> a.x;}
ostream& operator<<(ostream& os, const mint& a) { return os << a.x;}
//---------------------------------------------------------------

//↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓


ll h,w,ch,cw;
ll dh,dw; 
vector<string> f;
const int dx[4] = {1, 0, -1, 0};
const int dy[4] = {0, 1, 0, -1};


int main() {
    ios::sync_with_stdio(false);
    cin.tie(0);
    cout.tie(0);

    cin>>h>>w;
    cin>>ch>>cw;
    cin>>dh>>dw;

    ch--;cw--;
    dh--;dw--;

    f.resize(h);

    vec<vec<int>> dist(h,vec<int>(w,-1));

    dist[ch][cw] = 0;
    for(int i = 0; i<h; i++){
        cin >> f[i];
    }

    deque<pint> que;
    que.push_front(pint(ch,cw));

    dist[ch][cw] = 0;

    while(!que.empty()){
        auto e = que.front();
        que.pop_front();
        ll y = e.fi;
        ll x = e.se;

        for (int dir = 0; dir < 4; ++dir) {
            int nx = x + dx[dir], ny = y + dy[dir];
            if (nx < 0 || nx >= w || ny < 0 || ny >= h) continue;
            if (f[ny][nx] == '#') continue;
            if (dist[ny][nx] == -1) {
                dist[ny][nx] = dist[y][x];
                que.push_front(pint(ny, nx));
            }
            else if (chmin(dist[ny][nx], dist[y][x])) {
                que.push_front(pint(ny, nx));
            }
        }
        for (int nx = x - 2; nx <= x + 2; ++nx) {
            for (int ny = y - 2; ny <= y + 2; ++ny) {
                if (nx < 0 || nx >= w || ny < 0 || ny >= h) continue;
                if (f[ny][nx] == '#') continue;
                if (dist[ny][nx] == -1) {
                    dist[ny][nx] = dist[y][x] + 1;
                    que.push_back(pint(ny, nx));
                }  
                else if (chmin(dist[ny][nx], dist[y][x] + 1)) {
                    que.push_front(pint(ny, nx));
                } 
            }
        }
    }

    cout<<dist[dh][dw]<<endl;
    return 0;

}

Measured memory_bytes: 8732