// Slower C++ solution:
#include <iostream>

#include <cstdio>

#include <queue>

#include <cstring>

using namespace std;



//char s[1003][1003];

int vis[1003][1003];

struct node

{

    int x;int y;

};



int main()

{

    int h,w;

    cin>>h>>w;

    queue<node> q;

    memset(vis,0,sizeof(vis));

    for(int i=0;i<h;i++){

        for(int j=0;j<w;j++){

            char s;cin>>s;

            if(s=='#'){

                node a;a.x=i;a.y=j;

                q.push(a);

                vis[i][j]=1;

            }

        }

    }

    while(!q.empty()){

        node a;a=q.front();q.pop();

        if(a.x>0&&!vis[a.x-1][a.y]){

            vis[a.x-1][a.y]=vis[a.x][a.y]+1;

            node b;b.x=a.x-1;b.y=a.y;

            q.push(b);

        }

        if(a.y>0&&!vis[a.x][a.y-1]){

            vis[a.x][a.y-1]=vis[a.x][a.y]+1;

            node b;b.x=a.x;b.y=a.y-1;

            q.push(b);

        }

        if(a.x<h-1&&!vis[a.x+1][a.y]){

            vis[a.x+1][a.y]=vis[a.x][a.y]+1;

            node b;b.x=a.x+1;b.y=a.y;

            q.push(b);

        }

        if(a.y<w-1&&!vis[a.x][a.y+1]){

            vis[a.x][a.y+1]=vis[a.x][a.y]+1;

            node b;b.x=a.x;b.y=a.y+1;

            q.push(b);

        }

    }

    int ans=0;

    for(int i=0;i<h;i++){

        for(int j=0;j<w;j++){

            ans=max(ans,vis[i][j]);

            //cout<<vis[i][j];

        }

        //cout<<endl;

    }

    cout<<ans-1<<endl;

    return 0;

}


// Faster C++ solution for the same problem (measured speedup: 4.909721508304516x):
#include <iostream>

#include <string>

#include <queue>



using namespace std ;



struct Node

{

    int x , y ;

    bool black ;

} matrix [ 1000 ] [ 1000 ] ;



string arr [ 1000 ] ;



int main()

{

    int h , w , cnt = 0 , res = 0 ;

    cin >> h >> w ;

    for ( int i = 0 ; i < h ; i ++ )

        cin >> arr [ i ] ;

    queue<Node> q ;

    while ( !q.empty() )

        q.pop() ;

    for ( int i = 0 ; i < h ; i ++ )

    {

        for ( int j = 0 ; j < w ; j ++ )

        {

            matrix [ i ] [ j ].x = i ;

            matrix [ i ] [ j ].y = j ;

            matrix [ i ] [ j ].black = ( arr [ i ] [ j ] == '#' ) ;

            if ( matrix [ i ] [ j ].black )

            {

                q.push ( matrix [ i ] [ j ] ) ;

            }

        }

    }

    Node n ;

    while ( !q.empty() )

    {

        cnt = q.size() ;

        while ( cnt -- )

        {

            n = q.front() ;

            q.pop() ;

            if ( n.x > 0 )

            {

                if ( !matrix [ n.x - 1 ][ n.y ].black )

                {

                    matrix [ n.x - 1 ] [ n.y ].black = true ;

                    q.push ( matrix [ n.x - 1 ] [ n.y ] ) ;

                }

            }

            if ( n.y < w - 1 )

            {

                if ( !matrix [ n.x ] [ n.y + 1 ].black )

                {

                    matrix [ n.x ] [ n.y + 1 ].black = true ;

                    q.push ( matrix [ n.x ] [ n.y + 1 ] ) ;

                }

            }

            if ( n.x < h - 1 )

            {

                if ( !matrix [ n.x + 1 ] [ n.y ].black )

                {

                    matrix [ n.x + 1 ] [ n.y ].black = true ;

                    q.push ( matrix [ n.x + 1 ] [ n.y ] ) ;

                }

            }

            if ( n.y > 0 )

            {

                if ( !matrix [ n.x ] [ n.y - 1 ].black )

                {

                    matrix [ n.x ] [ n.y - 1 ].black = true ;

                    q.push ( matrix [ n.x ] [ n.y - 1 ] ) ;

                }

            }

        }

        res ++ ;

    }

    cout << res - 1 << endl ;

}