Harryxun/sft_time huggingface dataset:
### BUGGY CODE ###

n, m = map(int, input().split())
city = []
p_list = []
for i in range(m):
    p, y = map(int, input().split())
    p_list.append(p)
    city.append([p, y, i])
p_list.sort()
city.sort(key=lambda x: x[1])
city.sort()

n = 0
max_p = max(p_list)

for i in range(max_p + 1):
    for j in range(p_list.count(i)):
        city[n].append(str(p_list[n]).zfill(6) + (str(j + 1)).zfill(6))
        n += 1

city.sort(key=lambda x: x[2])
for i in range(m):
    print(city[i][3])


### FIXED CODE ###

n, m = map(int, input().split())
tmp = [list(map(int, input().split())) for i in range(m)]
city = [[] for i in range(n+1)]
answers = [''] * m

for i, (pref, year) in enumerate(tmp):
    city[pref].append([year, i])

for i in range(n+1):
    for j, (year, index) in enumerate(sorted(city[i])):
        ans = str(i).zfill(6) + str(j+1).zfill(6)
        answers[index] = ans

print(*answers, sep='\n')
### BUGGY CODE ###

N,K = map(int, input().split())
a = list(map(int, input().split()))

cond = []
for i in range(len(a)):
    for j in range(i, len(a)):
        cond.append(sum(a[i:j+1]))

ans = 0
for i in reversed(range(40)):
    b = ans + 2**i
    cnt = 0
    for c in cond:
        if c&b==b:
            cnt += 1
    if cnt>=K:
        ans = b

print(ans)


### FIXED CODE ###

N,K = map(int, input().split())
a = list(map(int, input().split()))

b = [0]
for ai in a:
    b.append(b[-1]+ai) 

cond = []
for i in range(N+1):
    for j in range(i+1, N+1):
        cond.append(b[j]-b[i])

ans = 0
for i in reversed(range(40)):
    b = ans + 2**i
    cnt = 0
    for c in cond:
        if c&b==b:
            cnt += 1
    if cnt>=K:
        ans = b

print(ans)
### BUGGY CODE ###

# -*- coding:utf-8 -*-

while True:
    n = int(input())
    print(n,':',sep='',end=' ')
    array = []
    count = 0
    while True:
        for i in range(2,n+1):
            if n%i == 0 and i != n:
                array.append(i)
                n = int(n/i)
                break
            if i == n-1:
                count += 1
                break
        if count == 15:
            break
    array.append(n)
    for i in range(len(array)):
        print(array[i],end=' ')
        print('')

### FIXED CODE ###

# -*- coding:utf-8 -*-

n = int(input())
print(str(n)+':',end='')
array = []
count = 0
while True:
    if n == 999993031:
        break
    for i in range(2,n+1):
        if n%i == 0 and i != n:
            array.append(i)
            n = int(n/i)
            break
        if i == n:
            count += 1
            break
    if count == 24:
        break

array.append(n)
for i in range(len(array)):
    print(' ',array[i],sep = '',end='')
print('')
### BUGGY CODE ###

n = int(input())
L = sorted(map(int,input().split()))
ans = 0

for i in range(n):
    for j in range(i+1,n):
        for k in range(j+1,n):
            a = L[i]
            b = L[j]
            c = L[k]
            
            if a < b + c:
                if b < c + a:
                    if c < a + b:
                        ans += 1
                    else:
                        break
                else:
                    break
            else:
                break
            
print(ans)

### FIXED CODE ###

import bisect
#二分探索をするライブラリ

n = int(input())
L = sorted(map(int,input().split()))
ans = 0

# c <= b <= a とする

for i in range(n-2):
    for j in range(i+1,n-1):
        a = L[n-1-i]
        b = L[n-1-j]
        
        if a-b < b:
            ans += (n-1-j) - bisect.bisect_left(L,a-b+1)
        
print(ans)
### BUGGY CODE ###

import sys
N,M = map(int,sys.stdin.readline().split())
start = []
goal = []
for i in range(M):
    a,b = map(int,sys.stdin.readline().split())
    if a == 1:
        start.append(b)
    if b == N:
        goal.append(a)
ans = 'IMPOSSIBLE'
for i in range(1,N+1):
    if i in start and i in goal:
        ans = 'POSSIBLE'
        break
print(ans)

### FIXED CODE ###

import sys
N,M = map(int,sys.stdin.readline().split())
start = []
goal = []
for i in range(M):
    a,b = map(int,sys.stdin.readline().split())
    if a == 1:
        start.append(b)
    if b == N:
        goal.append(a)
ans = 'IMPOSSIBLE'
seta = set(start)
setg = set(goal)
for i in seta:
    if i in setg:
        ans = 'POSSIBLE'
        break
print(ans)
### BUGGY CODE ###

n = int(input())
d = list(map(int,input().split()))
d.sort()
m = int(input())
t = list(map(int,input().split()))
t.sort()
for x in d:
    if x > t[0]:
        break
    elif x ==t[0]:
        t.pop(0)
    else:
        continue
    if len(t)==0:
        break
if len(t)==0:
    print("YES")
else:
    print("NO")


### FIXED CODE ###

from itertools import accumulate
from math import*
from collections import deque
from collections import defaultdict
from itertools import permutations
from heapq import*
from collections import Counter
from itertools import*
from bisect import bisect_left,bisect_right
from copy import deepcopy
inf = 10**18
mod = 10**9+7
from functools import reduce
import sys
sys.setrecursionlimit(10**7)

input()
d = Counter(map(int,input().split()))
input()
t = Counter(map(int,input().split()))
d.subtract(t)
if -d:
    print("NO")
else:
    print("YES")
### BUGGY CODE ###

#import random

def putmx(lis,mx):
  ret=[]
  lis.sort(key=lambda x: x[0],reverse=True)
  for i in lis:
    if i[0]!=mx:
      break
    ret.append(i[1])
  return ret
  

h,w,m=map(int,input().split())
hl=[0]*h
wl=[0]*w
hb=[]
wb=[]
bmb=[]
for i in range(h):
  bmb.append([])
  hb.append([0,i])
for i in range(w):
  wb.append([0,i])
for i in range(m):
  hh,ww=map(int,input().split())
  hh-=1
  ww-=1
  bmb[hh].append(ww)
  hb[hh][0]+=1
  wb[ww][0]+=1
  hl[hh]+=1
  wl[ww]+=1
mhb=max(hl)
mwb=max(wl)
hmx=putmx(hb,mhb)
wmx=putmx(wb,mwb)

#print(hb,wb,hmx,wmx)
fl=False
for i in hmx:
  for j in wmx:
    if not j in bmb[i]:
      print(mhb+mwb)
      fl=True
      break
  if fl:
    break
else:
  print(mhb+mwb-1)



### FIXED CODE ###

#import random

def putmx(lis,mx):
  ret=[]
  for (i,j) in zip(range(len(lis)),lis):
    if j==mx:
      ret.append(i)
  return ret
  

h,w,m=map(int,input().split())
hb=[0]*h
wb=[0]*w
bmb=[]
for i in range(h):
  bmb.append({-1})
for i in range(m):
  hh,ww=map(int,input().split())
  hh-=1
  ww-=1
  bmb[hh].add(ww)
  hb[hh]+=1
  wb[ww]+=1
mhb=max(hb)
mwb=max(wb)
hmx=putmx(hb,mhb)
wmx=set(putmx(wb,mwb))

#print(hb,wb,hmx,wmx)
fl=False
for i in hmx:
  if wmx|bmb[i]!=bmb[i]:
    print(mhb+mwb)
    break
else:
  print(mhb+mwb-1)

#print(hmx,wmx,bmb)
### BUGGY CODE ###

# -*- coding: utf-8 -*-
N,M = map(int,input().split())

# j = M
# I=int(j)
# s=0
# R=int(I)
# L=[]

# while s==0:
#     for i in range(2,R+1):
#         if I%i==0:
#             I=I/i
#             if I==1:
#                 s=1
#             L.append(i)
#             break
# print(L)
# ans = 1
# for l in L:
#     if l >= N:
#         ans = max(M//l,ans)

i = 1
ans = 0

if M%N == 0:
    ans = max(ans,M//N)

while M//N >= i:
    if M%i == 0:
        if M//i >= N:
            ans = max(ans,i)
    i += 1

print(ans)


### FIXED CODE ###

N,M = map(int,input().split())
ans = 1
i = 1
while i*i <= M:
    if M%i == 0 and M//N >= i:
        ans = max(ans,i)
        if M //i *N <= M:
            ans = max(ans,M//i)
    i += 1
print(ans)
### BUGGY CODE ###

l, r = map(int, input().split())

mod = 2019
ans = mod
for i in range(l, r):
    res = 0
    for j in range(i+1, r+1):
        res = (i*j) % mod
        ans = min(ans, res)
    if res == 0:
        print(ans)
        exit()

print(ans)

### FIXED CODE ###

l, r = map(int, input().split())

mod = 2019
ans = mod
for i in range(l, r):
    for j in range(i+1, r+1):
        res = (i*j) % mod
        ans = min(ans, res)
        if res == 0:
            print(ans)
            exit()

print(ans)
### BUGGY CODE ###

n, k = map(int, input().split())
A = list(map(int, input().split()))

score = [1] * (n - k + 1)

for i in range(n - k + 1): #iはスタート地点
  for j in range(i, i + k): #Aのj番目の要素をかける
    score[i] = score[i] * A[j]
  
for i in range(len(score) - 1):
  if score[i] < score[i + 1]:
    print("Yes")
  else:
    print("No")

### FIXED CODE ###

n, k = map(int, input().split())
A = list(map(int, input().split()))

for i in range(n - k): #iはスタート地点
    old = A[i] #Aのj番目の要素をかける
    new = A[i + k]
    
    if old < new:
        print("Yes")
    else:
        print("No")
### BUGGY CODE ###

import sys
input = sys.stdin.readline


n = int(input())
routes = []
ans = [[0]*n for i in range(n)]
edges = [[]for _ in range(n)]
used = [0]*n

for i in range(n-1):
    a, b = map(int, input().split())
    routes.append([a-1, b-1])
    edges[a-1].append(b-1)

sort_routes = sorted(routes)

for node in range(n):
    unanle = used[node]
    count = 1
    if count == unanle:
        count += 1
    for to in edges[node]:
        ans[node][to] = count
        used[to] = count
        count += 1
        if count == unanle:
            count += 1

print(max(used))
for _from, to in routes:
    print(ans[_from][to])

### FIXED CODE ###

import sys
input = sys.stdin.readline


n = int(input())
routes = []
dic = [{}] * n
edges = [[]for _ in range(n)]
used = [0]*n

for i in range(n-1):
    a, b = map(int, input().split())
    routes.append([a-1, b-1])
    edges[a-1].append(b-1)

for node in range(n):
    unanle = used[node]
    count = 1
    if count == unanle:
        count += 1
    for to in edges[node]:
        dic[node][to] = count
        used[to] = count
        count += 1
        if count == unanle:
            count += 1

print(max(used))
for _from, to in routes:
    print(dic[_from][to])
### BUGGY CODE ###

N, K = [int(x) for x in input().split()]

# sushi
s = {}
for i in range(N):
    t, d = [int(x) for x in input().split()]
    if not t in s:
        s[t] = [d]
    else:
        s[t].append(d)

# 各スシのMax
m = [max(v) for k, v in s.items()]
m.sort(reverse=True)

s2 = {}
all2 = []
for k in s.keys():
    s2[k] = sorted(s[k])
    s2[k].pop()
    all2 += s2[k]
all2.sort(reverse=True)

# スシ種類
# kinds = len(set([k for k in s.keys()]))
kinds = len(m)

ans = 0
for i in range(1, min(K, kinds) + 1):
    addM = m[:i]
    addAll2 = all2[:K - i]
    newAns = sum(addM) + sum(addAll2) + i ** 2
    ans = max(ans, newAns)

print(ans)



### FIXED CODE ###

N, K = [int(x) for x in input().split()]

# sushi
s = {}
for i in range(N):
    t, d = [int(x) for x in input().split()]
    if not t in s:
        s[t] = [d]
    else:
        s[t].append(d)

# 各スシのMax
m = [max(v) for k, v in s.items()]
m.sort(reverse=True)

s2 = {}
all2 = []
for k in s.keys():
    s2[k] = sorted(s[k])
    s2[k].pop()
    all2 += s2[k]
all2.sort(reverse=True)

# スシ種類
# kinds = len(set([k for k in s.keys()]))
kinds = len(m)

import itertools

acM = list(itertools.accumulate(m))
acAll2 = list(itertools.accumulate(all2))

ans = 0
# for i in range(1, min(K, kinds) + 1):
for i in range(0, min(K, kinds)):
    # addM = m[:i]
    # addAll2 = all2[:K - i]
    # newAns = sum(addM) + sum(addAll2) + i ** 2
    t1 = acM[i]
    idx = K - i - 2
    t2 = acAll2[idx] if idx >= 0 and idx < len(acAll2)  else 0
    newAns = t1 + t2 + (i + 1) ** 2
    ans = max(ans, newAns)

print(ans)

pass
### BUGGY CODE ###

from collections import defaultdict
def divisors(n):
    divisors = set()
    for i in range(1, int(n**0.5)+1):
        q, r = divmod(n, i)
        if not r:
            divisors.add(i)
            divisors.add(q)
    return divisors

n = int(input())
*A, = map(int, input().split())
B = [divisors(a) for a in A]
d = defaultdict(int)
for b in B:
    for c in b:
        d[c] += 1
print(max(k for k, v in d.items() if v >= n-1))

### FIXED CODE ###

from fractions import gcd

n = int(input())
*A, = map(int, input().split())
B = A[::-1]
L, R = [0]*(n+1), [0]*(n+1)
for i in range(n):
    L[i+1] = gcd(L[i], A[i])
    R[i+1] = gcd(R[i], B[i])
L, R = L[:n], R[:n][::-1]
print(max(gcd(l, r) for l, r in zip(L, R)))
### BUGGY CODE ###


from numba import njit,i8
import numpy as np


n,k = map(int,input().split())
p = np.array([int(i)-1 for i in input().split()],np.int64)
c = np.array(list(map(int,input().split())),np.int64)

#@njit(i8(i8,i8[:],i8[:]), cache = True)
def calc_score(x,p,c):
    n = p.size
    score = 0
    score_list = np.zeros(n,np.int64)
    cnt = 0
    visit = [0]*n
    while not visit[p[x]]:
        x = p[x]
        visit[x] = 1
        cnt += 1
        if cnt<=k:
            score += c[x]
            score_list[cnt-1] = score
        else:
            return score_list[:k].max()
    
    if score>0:
        if k%cnt>0:
            tmp_max = score_list[:k%cnt].max()
        else:
            tmp_max = 0
        return tmp_max + (k//cnt) * score
    else:
        return score_list[:cnt].max()

ans = max(calc_score(i,p,c) for i in range(n))
print(ans)

### FIXED CODE ###

#出来るだけループして端数を全部みるだとうまくいかない（最初と最後に負のスコアが固まっている場合など）

from numba import njit,i8
import numpy as np


n,k = map(int,input().split())
p = np.array([int(i)-1 for i in input().split()],np.int64)
c = np.array(list(map(int,input().split())),np.int64)

@njit(i8(i8,i8[:],i8[:]), cache = True)
def calc_score(x,p,c):
    n = p.size
    score = 0
    score_list = np.zeros(n,np.int64)
    cnt = 0
    visit = [0]*n
    while not visit[p[x]]:
        x = p[x]
        visit[x] = 1
        cnt += 1
        if cnt<=k:
            score += c[x]
            score_list[cnt-1] = score
        else:
            return score_list[:k].max()
    
    if score>0:
        tmp = np.arange(cnt)
        return (score_list[tmp] + ((k-1-tmp)//cnt) * score).max()
    else:
        return score_list[:cnt].max()

ans = max(calc_score(i,p,c) for i in range(n))
print(ans)
### BUGGY CODE ###

def main():
  from collections import defaultdict
  from heapq import heappush,heappop
  inf=2**31-1
  n,m,*t=map(int,open(0).read().split())
  edge=defaultdict(list)
  used,d={},{}
  l=set()
  for a,b,c in zip(t[::3],t[1::3],t[2::3]):
    if b<a:a,b=b,a
    x,y=a+n*c,b+n*c
    if b==n:l|={y}
    edge[a].append((1,x))
    edge[b].append((1,y))
    ex,ey=edge[x].append,edge[y].append
    ex((0,a))
    ex((0,y))
    ey((0,b))
    ey((0,x))
    used[a]=used[b]=used[x]=used[y]=True
    d[y]=inf
  used[1]=False
  edgelist=[]
  for e in edge[1]:
    heappush(edgelist,e)
  while edgelist:
    c,v=heappop(edgelist)
    if not used[v]:
      continue
    d[v]=c
    used[v]=False
    for e in edge[v]:
      if used[e[1]]:
        heappush(edgelist,(e[0]+c,e[1]))
  a=min([d[i]for i in l]or[inf])
  print([a,-1][a==inf])
if __name__=='__main__':
  main()

### FIXED CODE ###

def main():
  from heapq import heappush,heappop,heapify
  inf=2**31-1
  n,m,*t=map(int,open(0).read().split())
  z=[]
  for a,b,c in zip(t[::3],t[1::3],t[2::3]):
    z.extend([a,b,a+n*c,b+n*c])
  z={i:v for v,i in enumerate(sorted(set(z)))}
  try:
    z[1]
  except:
    print(-1)
    exit()
  edge=[[]for _ in range(len(z))]
  d={}
  l=[]
  for a,b,c in zip(t[::3],t[1::3],t[2::3]):
    if b<a:a,b=b,a
    i,j,x,y=z[a],z[b],z[a+n*c],z[b+n*c]
    if b==n:
      l.append(y)
    edge[i].append((1,x))
    edge[j].append((1,y))
    edge[x].extend([(0,i),(0,y)])
    edge[y].extend([(0,j),(0,x)])
  used=[False]+[True]*~-len(z)
  d=[0]+[inf]*~-len(z)
  edgelist=edge[0]
  heapify(edgelist)
  while edgelist:
    m=heappop(edgelist)
    if not used[m[1]]:
      continue
    d[m[1]]=m[0]
    used[m[1]]=False
    for e in edge[m[1]]:
      if used[e[1]]:
        heappush(edgelist,(e[0]+m[0],e[1]))
  a=min([d[i]for i in l]or[inf])
  print([a,-1][a==inf])
if __name__=='__main__':
  main()
### BUGGY CODE ###

temp = input()
temp = temp.split()
room = int(temp[0])
passage = int(temp[1])
adjlist = {}
visited = [0] * (room + 1) 
finalans = []
finalans.append(0)
findmin1 = {}
for i in range(passage):
    inpu = input()
    inpu = inpu.split()
    firstnode = int(inpu[0])
    secnode = int(inpu[1])
    if firstnode == 1:
        findmin1[secnode] = 1 
    if secnode == 1 :
        findmin1[firstnode] = 1 
    
    if firstnode not in adjlist:
        adjlist[firstnode] = []
    if secnode not in adjlist:
        adjlist[secnode] = []
        
    adjlist[firstnode].append(secnode)
    adjlist[secnode].append(firstnode)

flag = 0 
for i in range(2, room + 1):
    temparr = []
    ans = -1 
    visited = [0] * (room + 1) 
    if i not in adjlist:
        flag = 1 
        break
    templist = adjlist[i]
    if i in findmin1:
        finalans.append(1)
        continue 
    for j in templist:
        visited[j] = 1
        temparr.append((j, j))
    while True:
        if len(temparr) == 0:
            break
        getans = 0 
        newarr = []
        for node in temparr:
            newnode = node[0]
            firstnode = node[1]
            if newnode not in adjlist:
                continue 
            if newnode in findmin1:
                getans = 1 
                ans = firstnode
                break
            for j in adjlist[newnode]:
                if visited[j] == 1 :
                    continue 
                visited[j] = 1 
                newarr.append((j, firstnode))
        
        if getans == 1:
            break
        
        temparr = newarr[::]
    
    if ans == -1:
        flag = 1 
        break
    finalans.append(ans)

if flag == 1:
    print("No")
#print(adjlist)
else:
    print("Yes")
    for i,j in enumerate(finalans):
        if i == 0 :
            continue 
        print(j)
#print(finalans)

### FIXED CODE ###

from collections import deque
newarr = input()
newarr = newarr.split()
n = int(newarr[0])
m = int(newarr[1])
dicts = {}
ans = [0] * (n + 1)
for line in range(m):
    newarr = input()
    newarr = newarr.split()
    froom = int(newarr[0])
    sroom = int(newarr[1])
    if froom not in dicts:
        dicts[froom] = []
    if sroom not in dicts:
        dicts[sroom] = []
    dicts[froom].append(sroom)
    dicts[sroom].append(froom)
queue = deque([])
if 1 not in dicts:
    print("No")
else:
    ans[1] = 1
    curarr = dicts[1]
    for i in curarr:
        queue.append(i)
        ans[i] = 1 
    while queue:
        curitem = queue.popleft()
        if curitem not in dicts:
            continue 
        curarr = dicts[curitem]
        for i in curarr:
            if ans[i] == 0:
                ans[i] = curitem 
                queue.append(i)

    finalans = []
    flag = 0 
    for i in range(2, n + 1):
        if i == 0 :
            flag = 1 
            break 
        finalans.append(ans[i])
    if flag == 1:
        print("No")
    else:
        print("Yes")
        for i in finalans:
            print(i)
### BUGGY CODE ###

import fractions as math
N=int(input())
A=list(map(int,input().split()))
t=1
for i in A:
  t=(t*i)//math.gcd(t,i)
ans=0
for i in A:
  ans+=t//i
  ans%=(10**9+7)
print(ans)

### FIXED CODE ###

import fractions 
N=int(input())
A=list(map(int,input().split()))
t=A[0]
for i in range(1,N):
  t=(t*A[i])//fractions.gcd(t,A[i])
ans=0
for i in range(N):
  ans+=t//A[i]
print(ans%(10**9+7))
### BUGGY CODE ###

def main():
    H, W = map(int, input().split())
    g = [str(input()) for _ in range(H)]
    ans = 0
    for h in range(H):
        for w in range(W):
            if g[h][w] != '#':
                cnt = 1
                dh = [1, -1, 0, 0]
                dw = [0, 0, 1, -1]
                for i in range(4):
                    nh = h + dh[i]
                    nw = w + dw[i]
                    while True:
                        if 0 <= nh < H and 0 <= nw < W and g[nh][nw] == '.':
                            cnt += 1
                            nh += dh[i]
                            nw += dw[i]
                        else:
                            break
                ans = max(ans, cnt)
    print(ans)

main()

### FIXED CODE ###

def main():
    H, W = map(int, input().split())
    g = [str(input()) for _ in range(H)]
    LW = [[0] * W for _ in range(H)]
    LH = [[0] * W for _ in range(H)]
    for h in range(H):
        cnt = 0
        for w in range(W):
            if g[h][w] == '.':
                cnt += 1
            else:
                for i in range(1, cnt+1):
                    LW[h][w-i] = cnt
                LW[h][w] = 0
                cnt = 0
        else:
            for i in range(cnt):
                LW[h][w-i] = cnt
    for w in range(W):
        cnt = 0
        for h in range(H):
            if g[h][w] == '.':
                cnt += 1
            else:
                for i in range(1, cnt+1):
                    LH[h-i][w] = cnt
                LH[h][w] = 0
                cnt = 0
        else:
            for i in range(cnt):
                LH[h-i][w] = cnt
    ans = 0
    for h in range(H):
        for w in range(W):
            if g[h][w] != '#':
                ans = max(ans, LH[h][w] + LW[h][w] - 1)
    print(ans)
main()
### BUGGY CODE ###

#import copy
import sys
 
H, W = map(int, input().split())
#dist_matrix = [[10000] * W for i in range(H)]
black_h_list = []
black_w_list = []
for i in range(H):
  line_list = list(input())
  for j in range(W):
    if line_list[j] == "#":  
      black_h_list.append(i)
      black_w_list.append(j)
 
#print(black_h_list)
#print(black_w_list)

if len(black_h_list) == H*W:
  print(0)
  sys.exit()
  
max_value = 1
for i in range(H):
  for j in range(W):
    min_dist = H+W+2
    if j > 0:
      min_dist = last_dist+1
      
    for k in range(len(black_h_list)):
      if i-black_h_list[k] >= min_dist:
        continue
      elif black_h_list[k]-i >= min_dist:
        break
      
      dist = abs(i-black_h_list[k]) + abs(j-black_w_list[k])
      if max_value >= dist:
        min_dist = dist
        break
      elif min_dist > dist:
        min_dist = dist        
    #dist_matrix[i][j] = min_dist
    if max_value < min_dist:
      max_value = min_dist
      
    last_dist = min_dist
    #print(str(i) + "," + str(j) + "," + str(min_dist))

#print(dist_matrix)
    
print(max_value)

### FIXED CODE ###

from collections import deque
import sys
input = sys.stdin.readline
 
H, W = map(int, input().split())
mark_matrix = [[True]*(W+2)]
#mark_matrix.extend([[True]+[False]*(W)+[True] for _ in range(H)])
mark_matrix.extend([[True]+[x!='.' for x in input()] for _ in range(H)])
mark_matrix[H].append(True)
mark_matrix.append([True]*(W+2))
#queue = []
queue = deque()
for i in range(1,H+1):
  for j in range(1,W+1):
    if mark_matrix[i][j]:
      queue.append((i,j))
#  line = input()
#  for j,ch in enumerate(line):
#    if ch == "#":
#      mark_matrix[i+1][j+1] = True
#      queue.append((i+1,j+1))
#for i in range(1,H+1):
#  mark_matrix[i][0] = True
#  mark_matrix[i][W+1] = True
#for j in range(W+2):
#  mark_matrix[0][j] = True
#  mark_matrix[H+1][j] = True
#print(mark_matrix)
 
#cnt = 0
#print(queue)
max_value = 0
while(True):
  #print(len(queue))
  if len(queue) == 0:
    break
  
  new_queue = deque()
  for i,j in queue:
  
    if not mark_matrix[i-1][j]:
      mark_matrix[i-1][j] = True
      #queue.append((i-1,j))
      new_queue.append((i-1,j))
    if not mark_matrix[i+1][j]:
      mark_matrix[i+1][j] = True
      #queue.append((i+1,j))
      new_queue.append((i+1,j))
    if not mark_matrix[i][j-1]:
      mark_matrix[i][j-1] = True
      #queue.append((i,j-1))
      new_queue.append((i,j-1))
    if not mark_matrix[i][j+1]:
      mark_matrix[i][j+1] = True
      #queue.append((i,j+1))
      new_queue.append((i,j+1))
 
  if len(new_queue) == 0:
    break
  else:
    queue = new_queue
    max_value += 1
  
#print(cnt)
#print(dist_matrix)
print(max_value)