Problem:
B: Hokkaido University Hard

注意

　問題設定は A 問題と同一のものですが、制約のみが異なりますのでご注意ください。

物語

　北海道大学に合格し、新たな生活の始まりに心を躍らせるほむらちゃん。しかし彼女の前には、とてつもなく広いキャンパスが待ち受けていた...。

　「え...次の授業に間に合わないんだけど...」

問題

　北海道大学札幌キャンパスは異常に広いことで有名です。札幌キャンパスは縦に H マス、横に W マス並んだ長方形のマス目で表現されます。北から i マス、西から j マス進んだマスを (i,j) で表すことにします。キャンパス内にはいくつか建物があり、マス (i,j) で表される位置に建物がある場合は 'B' 、ない場合は '.' が c_{i,j} に書かれています。

　北海道大学の新入生のほむらちゃんは、キャンパスのあまりの広さに驚愕し、建物間の移動が心配になってきました。そこで、建物のある 2 つのマスのうち、最も遠い組はどれくらい離れているのかが気になりました。ここで、2 つのマスの組 (i,j) , (i',j') の間の距離を |i-i'|+|j-j'| と定義します。

　ほむらちゃんは、自分にはこの問題は難しいと思い、同級生のあなたに助けを求めてきました。ほむらちゃんの代わりに答えを求めてください。

入力形式

H W
c_{11}c_{12} ... c_{1W}
:
c_{H1}c_{H2} ... c_{HW}

制約

2 \leq H,W \leq 10^3

H,W は整数

c_{i,j} は 'B' か '.' のいずれかである。

c_{i,j} のうち少なくとも 2 つは 'B' である。

出力形式

答えを表す整数を 1 行に出力せよ。

入力例 1

3 3
B.B
..B
.BB

出力例 1

4

(1,1) と (3,3) の 2 点間が最長です。

入力例 2

4 3
B..
B..
...
...

出力例 2

1

隣り合う位置が最長になる場合もあります。

入力例 3

6 6
...B..
B.B.B.
.B.B.B
...B.B
.B..B.
..B...

出力例 3

7

Solution in C# (judge verdict: Accepted)

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using static System.Console;
using static System.Math;

namespace AtTest.HUPC_day2
{
    class B
    {
        static void Main(string[] args)
        {
            Method(args);
        }

        static void Method(string[] args)
        {
            int[] hw = ReadInts();
            int h = hw[0];
            int w = hw[1];
            List<int[]> poses = new List<int[]>();
            List<int> plus = new List<int>();
            List<int> minus = new List<int>();
            for(int i = 0; i < h; i++)
            {
                string s = Read();
                for(int j = 0; j < w; j++)
                {
                    if (s[j] == 'B')
                    {
                        plus.Add(i + j);
                        minus.Add(i - j);
                    }
                }
            }
            plus.Sort();
            minus.Sort();

            WriteLine(Max(plus[plus.Count - 1] - plus[0],
                minus[minus.Count - 1] - minus[0]));
        }

        private static string Read() { return ReadLine(); }
        private static char[] ReadChars() { return Array.ConvertAll(Read().Split(), a => a[0]); }
        private static int ReadInt() { return int.Parse(Read()); }
        private static long ReadLong() { return long.Parse(Read()); }
        private static double ReadDouble() { return double.Parse(Read()); }
        private static int[] ReadInts() { return Array.ConvertAll(Read().Split(), int.Parse); }
        private static long[] ReadLongs() { return Array.ConvertAll(Read().Split(), long.Parse); }
        private static double[] ReadDoubles() { return Array.ConvertAll(Read().Split(), double.Parse); }
    }
}