Problem:


Score : 500 points

Problem Statement

N players will participate in a tennis tournament. We will call them Player 1, Player 2, \ldots, Player N.

The tournament is round-robin format, and there will be N(N-1)/2 matches in total.
Is it possible to schedule these matches so that all of the following conditions are satisfied? If the answer is yes, also find the minimum number of days required.

Each player plays at most one matches in a day.

Each player i (1 \leq i \leq N) plays one match against Player A_{i, 1}, A_{i, 2}, \ldots, A_{i, N-1} in this order.

Constraints

3 \leq N \leq 1000

1 \leq A_{i, j} \leq N

A_{i, j} \neq i

A_{i, 1}, A_{i, 2}, \ldots, A_{i, N-1} are all different.

Input

Input is given from Standard Input in the following format:

N
A_{1, 1} A_{1, 2} \ldots A_{1, N-1}
A_{2, 1} A_{2, 2} \ldots A_{2, N-1}
:
A_{N, 1} A_{N, 2} \ldots A_{N, N-1}

Output

If it is possible to schedule all the matches so that all of the conditions are satisfied, print the minimum number of days required; if it is impossible, print -1.

Sample Input 1

3
2 3
1 3
1 2

Sample Output 1

3

All the conditions can be satisfied if the matches are scheduled for three days as follows:

Day 1: Player 1 vs Player 2

Day 2: Player 1 vs Player 3

Day 3: Player 2 vs Player 3

This is the minimum number of days required.

Sample Input 2

4
2 3 4
1 3 4
4 1 2
3 1 2

Sample Output 2

4

All the conditions can be satisfied if the matches are scheduled for four days as follows:

Day 1: Player 1 vs Player 2, Player 3 vs Player 4

Day 2: Player 1 vs Player 3

Day 3: Player 1 vs Player 4, Player 2 vs Player 3

Day 4: Player 2 vs Player 4

This is the minimum number of days required.

Sample Input 3

3
2 3
3 1
1 2

Sample Output 3

-1

Any scheduling of the matches violates some condition.



Sample input:
3
2 3
1 3
1 2


Sample output:
3

Submission status: Accepted

Solution code:
import sys
input=sys.stdin.readline
n=int(input())
outs=[[] for i in range(1000000)]
ins=[0]*1000000
for i in range(n):
    a_list=list(map(int,input().split()))
    for j in range(1,n-1):
        x1=min(i,a_list[j-1]-1)
        y1=max(i,a_list[j-1]-1)
        z1=x1*1000+y1
        x2=min(i,a_list[j]-1)
        y2=max(i,a_list[j]-1)
        z2=x2*1000+y2
        outs[z1].append(z2)
        ins[z2]+=1
q=[]
for i in range(n):
    for j in range(i+1,n):
        if ins[1000*i+j]==0:
            q.append(1000*i+j)
res=0
ans=0
while q:
    ans+=1
    v1_list=[]
    while q:
        v1=q.pop()
        res+=1
        v1_list.append(v1)
    for v1 in v1_list:
        for v2 in outs[v1]:
            ins[v2]-=1
            if ins[v2]==0:
                q.append(v2)
if res==n*(n-1)//2:
    print(ans)
else:
    print(-1)

Submission status: Accepted

Solution code:
def solve():
    N = int(input())
    Ass = []
    for _ in range(N):
        As = list(map(lambda x: int(x)-1, input().split()))
        Ass.append(As+[N])

    games = []
    numReadyss = [[0]*(N) for _ in range(N)]
    iAs = [0] * N
    for i in range(N):
        j = Ass[i][iAs[i]]
        if j > i: i, j = j, i
        numReadyss[i][j] += 1
        if numReadyss[i][j] >= 2:
            games.append((i, j))
    ans = 1
    numOK = 0
    while True:
        if not games:
            print(-1)
            return
        game2s = []
        for i, j in games:
            iAs[i] += 1
            i2 = Ass[i][iAs[i]]
            if i2 == N:
                numOK += 1
            else:
                if i2 > i: i, i2 = i2, i
                numReadyss[i][i2] += 1
                if numReadyss[i][i2] >= 2:
                    game2s.append((i, i2))
            iAs[j] += 1
            j2 = Ass[j][iAs[j]]
            if j2 == N:
                numOK += 1
            else:
                if j2 > j: j, j2 = j2, j
                numReadyss[j][j2] += 1
                if numReadyss[j][j2] >= 2:
                    game2s.append((j, j2))
        if numOK >= N:
            print(ans)
            return
        ans += 1
        games = game2s


solve()

Submission status: Accepted

Solution code:
import sys, time
def input():
	return sys.stdin.readline()[:-1]

n = int(input())
a = [list(map(int, input().split()))[::-1] for _ in range(n)]
#print(*a, sep="\n")
opponent = [-1 for _ in range(n)]
played = list(range(n))
match = 0
day = 0
while match < n*(n-1)//2:
	approved = False
	for i in played:
		if a[i] != []:
			opponent[i] = a[i].pop()-1
	played_next = []
	#print(opponent)
	for i in played:
		if opponent[i] != -1 and opponent[opponent[i]] == i:
			approved = True
			match += 1
			played_next += [i, opponent[i]]
			opponent[opponent[i]] = -1
			opponent[i] = -1
	#print(opponent)
	if not approved:
		print(-1)
		sys.exit()
	day += 1
	played = played_next
print(day)

Submission status: Accepted

Solution code:
import sys
input = sys.stdin.readline
from collections import deque

N = int(input())
A = [list(reversed(list(map(lambda x:int(x)-1,input().split())))) for i in range(N)]
B = {i:row for i,row in enumerate(A)}

end = 0
for k in range(8000):
    used = set()
    dels = []
    for i,q in B.items():
        if not q: continue
        if i in used: continue
        j = q[-1]
        if j in used: continue
        if A[j][-1] == i:
            A[j].pop()
            A[i].pop()
            used.add(i)
            used.add(j)
            if not A[i]:
                end += 1
                dels.append(i)
            if not A[j]:
                end += 1
                dels.append(j)
    if not used:
        print(-1)
        exit()
    if end == N:
        print(k+1)
        exit()
    for i in dels:
        del B[i]

print(N*(N-1)//2)

Submission status: Accepted

Solution code:
from collections import deque
import time

start = time.time() # なにこれ

n = int(input())
target_num = n*(n-1)//2

all_set = set()
a = [deque(list(map(int, input().split()))) for i in range(n)]
ans = 0

while True:
  cur_set = set()
  flag = False
  for i in range(n):
    if len(a[i]):
      tup = (min(i+1, a[i][0]), max(i+1, a[i][0]))
    else:
      continue
    if tup not in cur_set:
      cur_set.add(tup)
    elif tup in cur_set:
      all_set.add(tup)
      t1, t2 = tup
      a[t1-1].popleft()
      a[t2-1].popleft()
      flag = True
  ans += 1
  if len(all_set)==target_num:
    break
  if time.time()-start>1.8:
    print(1000*999//2)
    exit()
  if not flag:
    print(-1)
    exit()

print(ans)

Submission status: Accepted

Solution code:
import time
def main():
    N = int(input())
    a = [list(map(int, input().split())) for i in range(N)]
    start = time.time()
    now = [0] * N
    day = 0
    gamed_day = [-1] * N
    finished = 0
    while True:
        if time.time() - start > 1.6:
            print((N*(N-1))//2)
            break
        had_game = False
        all_finish = True
        for i in range(N-1, -1, -1):
            if now[i] < N-1 and gamed_day[i] != day:
                all_finish = False
                want = a[i][now[i]] - 1
                if gamed_day[want] != day:# 今日試合していない
                    if a[want][now[want]] - 1 == i:# 相手の試合相手が自分
                        now[want] += 1
                        now[i] += 1
                        if now[want] >= N-1:
                            finished += 1
                        if now[i] >= N-1:
                            finished += 1
                        gamed_day[i] = day
                        gamed_day[want] = day
                        had_game = True
                        # print(day+1, i+1, want+1)
        if all_finish or finished == N:
            if had_game:
                print(day+1)
            else:
                print(day)
            break
        if not had_game:
            print(-1)
            break
        day += 1
    # print(now)

if __name__ == "__main__":
    main()

Submission status: Accepted

Solution code:
import time
s_time = time.time()


n = int(input())
a = [list(map(int, input().split())) for i in range(n)]

memo = {}
for i in range(n):
    memo[i] = 0

cnt = 0
while True:
    visited = [False] * n
    flag = False
    for i in range(n):
        if memo[i] == len(a[0]):
            continue
        if visited[i] or visited[a[i][memo[i]] - 1]:
            continue
        visited[i] = True
        if i + 1 == a[a[i][memo[i]] - 1][memo[a[i][memo[i]] - 1]]:
            visited[a[i][memo[i]] - 1] = True
            flag = True
            tmp = memo[i]
            memo[i] += 1
            memo[a[i][tmp] - 1] += 1
    if flag:
        cnt += 1
    else:
        for i in memo:
            if memo[i] != len(a[0]):
                print(-1)
                exit()
        break
    if abs(s_time - time.time()) > 1.7:
        print(n*(n-1) //2)
        exit()
print(cnt)

Submission status: Accepted

Solution code:
import sys
from heapq import heappop, heappush
from operator import itemgetter
from collections import deque, defaultdict, Counter
from bisect import bisect_left, bisect_right
input = sys.stdin.readline
sys.setrecursionlimit(10 ** 7)
MOD = 10**9 + 7
INF = float('inf')


def sol():
    N = int(input())
    A = [deque()] + [deque(map(int, input().split())) for _ in range(N)]

    days = [0] * (N + 1)
    now = [0] * (N + 1)

    que = deque([i + 1 for i in range(N)])

    while que:
        i = que.popleft()
        if not A[i]:
            continue

        a = A[i].popleft()
        if now[a] == i:
            days[a] = days[i] = max(days[a], days[i]) + 1
            que.append(i)
            que.append(a)
            now[a] = now[i] = 0
        else:
            now[i] = a

    for i in range(1, N + 1):
        if A[i]:
            print(-1)
            return
    print(max(days))


sol()

Submission status: Accepted

Solution code:
import sys
input = sys.stdin.readline
N = int(input())
A = []
for i in range(N):
    A.append(list(map(int, input().split())))
index = [0]*(N+1)
ans = -2
for k in range(10000):
    today = set()
    flag = 0
    for j in range(N):
        if j+1 in today:
            continue
        if index[j+1] >= N-1:
            continue
        #print(j, index[j+1])
        opponent = A[j][index[j+1]]
        if A[opponent-1][index[opponent]] == j+1:
            if opponent not in today:
                index[opponent] += 1
                index[j+1] += 1
                today.add(opponent)
                today.add(j+1)
                flag = 1
    if flag == 0:
        if sum(index) == N*(N-1):
            ans = k
            break
        else:
            ans = -1
            break
    #print(index)

if ans == -2:
    print(N*(N-1)//2)
else:
    print(ans)

Submission status: Accepted

Solution code:
import time
start = time.time()
N = int(input())
A = [list(map(lambda x:int(x)-1,input().split())) for i in range(N)]
B = [0]*N
S = 0
ans = 0
while True:
    C = [0]*N
    for n in range(N):
        if C[n]==0 and B[n]!=N-1:
            b = A[n][B[n]]
            if C[b]==1: continue
            if A[b][B[b]]==n:
                B[n]+=1
                B[b]+=1
                C[n],C[b]=1,1
    if sum(C)==0:break
    ans +=1
    if time.time()-start>1.7:
        print(N*(N-1)//2)
        exit()
print(ans if sum(B)==N*(N-1) else -1)

Submission status: Accepted

Solution code:
import sys, time
def input():
	return sys.stdin.readline()[:-1]

n = int(input())
a = [list(map(int, input().split()))[::-1] for _ in range(n)]
#print(*a, sep="\n")
opponent = [-1 for _ in range(n)]
match = 0
day = 0
start_time = time.time()
while match < n*(n-1)//2:
	approved = False
	for i in range(n):
		if a[i] != [] and opponent[i] == -1:
			opponent[i] = a[i].pop()-1
	#print(opponent)
	for i in range(n):
		if opponent[i] != -1 and opponent[opponent[i]] == i:
			approved = True
			match += 1
			opponent[opponent[i]] = -1
			opponent[i] = -1
	#print(opponent)
	if not approved:
		print(-1)
		sys.exit()
	now = time.time()
	#print(start_time, now, now - start_time)
	if now-start_time > 1.6:
		print(n*(n-1)//2)
		sys.exit()
	day += 1
print(day)

Submission status: Accepted

Solution code:
rr = raw_input
rri = lambda: int(raw_input())
rrm = lambda: map(int, raw_input().split())

from collections import deque
def solve(N, A):
    # A as deques of values in [0, N)

    now = range(N)
    todo = N * (N - 1)
    for ans in range(1, N * N):
        later = set()
        for i in now:
            if A[i] and i not in later:
                j = A[i][0]
                if j not in later and A[j] and A[j][0] == i:
                    later.add(A[i].popleft())
                    later.add(A[j].popleft())
                    todo -= 2

        if not todo:
            return ans
        now = later
    return -1


N = rri()
A = []
for _ in xrange(N):
    row = rrm()
    A.append(deque(x-1 for x in row))
print solve(N, A)

Submission status: Accepted

Solution code:
import sys
input = sys.stdin.readline
N = int(input())
A = [[0] * (N-1)]+[list(map(int,input().split())) for _ in range(N)]

idx = [0] * (N+1)
cnt = 0
day = 0
flag_max = [False] * (N+1)
while cnt != N:
    
    error = True
    flag =[False] * (N+1)
    looplist = [i for i in range(1,N+1) if not(flag_max[i])]
    
    for i in looplist:
        if (flag[i]):continue
        tmp = A[i][idx[i]]
        if (flag[tmp]):continue
    
        if A[tmp][idx[tmp]] == i:
            idx[tmp] = idx[tmp] + 1
            idx[i] = idx[i] + 1
            if idx[tmp] == N-1:
                flag_max[tmp] = True
                cnt += 1
            if idx[i] == N-1:
                flag_max[i] = True
                cnt += 1
            flag[i] = True
            flag[tmp] = True
            error = False
    if error:
        print(-1)
        sys.exit()
    
    day += 1
            

    if day > 10000:
        print(N*(N-1)//2)
        sys.exit()
    
    
print(day)

Submission status: Accepted

Solution code:
import sys

N=int(input())
amat=[[-1]]
for i in range(N):
  alist=list(map(int,input().split()))
  amat.append(list(reversed(alist)))
  
#print(amat)
answer=0
matched_flag=[False]*(N+1)
for answer in range(1,N**3):
  if N>900 and answer>3000:
    print(N*(N-1)//2)
    sys.exit()
  
  matched_flag=[False]*(N+1)
  unchanged=True
  
  for i in range(1,N+1):
    if matched_flag[i] or len(amat[i]) == 0:
      continue
      
    ai_next = amat[i][-1]
    if amat[ai_next][-1]==i and not matched_flag[ai_next]:
      #print(i,ai_next,answer)
      matched_flag[amat[i].pop()]=True
      matched_flag[amat[ai_next].pop()]=True
      unchanged=False
  
  if unchanged:
    print(-1)
    sys.exit()
  else:
    for i in range(1,N+1):
      if len(amat[i])>0:
        break
    else:
      print(answer)
      sys.exit()

Submission status: Accepted

Solution code:
from collections import defaultdict, deque
outs = defaultdict(list)
ins = defaultdict(int)

def get_ab(h):
    return h // 10000, h % 10000

def get_hash(a, b):
    if a >= b:
        return 10000*a + b
    else:
        return 10000*b + a
v = []
N = int(input())
for i in range(N):
    nums = list(map(int, input().split()))
    pred = get_hash(i+1, nums[0])
    if pred not in v:
        v.append(pred)
    for j in range(len(nums)-1):
        now = get_hash(i+1, nums[j+1])
        outs[pred].append(now)
        ins[now] += 1
        pred = now

q = deque(v1 for v1 in v if ins[v1] == 0)
res = []
ans = 0
before = []
while q:
    v1 = q.popleft()
    res.append(v1)
    a, b = get_ab(v1)
    if (a in before) or (b in before):
        before = [a, b]
        ans += 1
    else:
        before.append(a)
        before.append(b)
    for v2 in outs[v1]:
        ins[v2] -= 1
        if ins[v2] == 0:
            q.append(v2)
if len(res) < (N*(N-1)) // 2:
    print(-1)
else:
    print(ans+1)

Submission status: Accepted

Solution code:
import pprint

n = int(input())
a = [list(map(int, input().split())) for i in range(n)]

day = 0
check = set(range(n))

while True:
    end = 1
    game = set()
    for i in check:
        if a[i] != []:
            end = 0
            if a[a[i][0]-1] != []:
                if a[a[i][0]-1][0]-1 == i:
                    game.add(i)
                    game.add(a[i][0]-1)
    if end == 0:
        if game == set():
            print(-1)
            exit()
        else:
            for i in game:
                a[i].pop(0)
    else:
        print(day)
        exit()
    day += 1
    check = game

Submission status: Accepted

Solution code:
import sys
input = sys.stdin.readline
N=int(input())
xs = [None]
for _ in range(N):
    xs.append(list(map(int, input().split()))[::-1])
tops = [None] * (N+1)
for i in range(N):
    i += 1
    tops[i] = xs[i].pop()

cc = 0
rr = 0
ns = [i+1 for i in range(N)]
while True:
    vs = set()
    nn = False
    nns = []
    for i in ns:
        j = tops[i]
        if j == None:
            continue
        if i in vs or j in vs:
            continue
        if tops[j] == i:
            nn = True
            if len(xs[i]):
                tops[i] = xs[i].pop()
            else:
                tops[i] = None
                cc += 1
            if len(xs[j]):
                tops[j] = xs[j].pop()
            else:
                tops[j] = None
                cc += 1
            vs.add(i)
            vs.add(j)
            nns.append(i)
            nns.append(j)
    ns = nns
    rr += 1
    if cc == N:
        break
    if not nn:
        rr = -1
        break

print(rr)

Submission status: Accepted

Solution code:
import sys
from collections import defaultdict


def dfs(root, links):
    status = {}
    topological = []
    q = [(r, 0, 1) for r in root]
    while q:
        node = q.pop()
        if node[1] == 0:
            v, _, d = node
            q.append((v, 1))
            status[v] = 1
            d += 1
            for u in links[v]:
                if u in status:
                    if status[u] == 1:
                        return False
                else:
                    q.append((u, 0, d))
        else:
            v = node[0]
            status[v] = 2
            topological.append(v)
    topological.reverse()
    return topological


n = int(input())
links = defaultdict(set)
may_root = set()
lines = sys.stdin.readlines()
matches = []
for i in range(n):
    line = lines[i]
    aaa = list(map(int, line.split()))
    match_order = []
    for j in aaa:
        j -= 1
        a, b = (i, j) if i < j else (j, i)
        key = a * n + b
        match_order.append(key)
    matches.append(match_order)
    may_root.add(match_order[0])

for i in range(n):
    kkk = matches[i]
    prev = kkk[0]

    for key in kkk[1:]:
        links[prev].add(key)
        may_root.discard(key)
        prev = key

if not may_root:
    print(-1)
    exit()

topological = dfs(may_root, links)
if topological == False:
    print(-1)
    exit()

ans = 0
depth = defaultdict(lambda: 1)
for v in topological:
    d = depth[v] + 1
    for u in links[v]:
        depth[u] = max(depth[u], d)

print(max(depth.values()))

Submission status: Accepted

Solution code:
from sys import setrecursionlimit as SRL, stdin

SRL(10 ** 7)
rd = stdin.readline
rrd = lambda: map(int, rd().strip().split())

q = [[]]
l = [0] * 1005
d = [0] * 1005
hv = [0] * 1005

def dfs(x,y):
    hv[x] = 1
    for i in range(l[x],n-1):

        if q[x][i] == y:
            l[x] = i+1
            hv[x] = 0

            d[q[x][i]] += 1
            d[x] += 1
            d[x] = max(d[x],d[q[x][i]])
            d[q[x][i]] = max(d[x], d[q[x][i]])

            return
        if hv[q[x][i]]:
            print(-1)
            exit(0)
        dfs(q[x][i],x)
        d[x] = max(d[q[x][i]],d[x])


    hv[x] = 0
    l[x] = n

n = int(input())
for i in range(n):
    a = list(rrd())
    q.append(a)

for i in range(1,n+1):
    dfs(i,0)

print(max(d))

Submission status: Accepted

Solution code:
import sys
input = sys.stdin.readline
sys.setrecursionlimit(10**9)

from collections import deque

N = int(input())

A = [0 for i in range(N)]
for i in range(N) :
    L = list(map(int,input().split()))
    for j in range(len(L)) :
        L[j] -= 1
    A[i] = deque(L)

#print(A)
ans = 0
flg = 0

zuru = 0

while flg == 0 :
    zuru += 1
    cnt = 0
    cnt2 = 0
    flg = 1

    if zuru >= 10**4 :
        ans = 499500
        print(ans)
        exit()
    
    for i in range(N) :
        if len(A[i]) == 0 :
            cnt += 1
        elif A[i][0] == -1 :
            A[i].popleft()
        elif A[i][0] < i :
            cnt2 += 1
            continue
        elif i == A[A[i][0]][0] :
            a = A[i].popleft()
            A[a][0] = -1
            flg = 0
        else :
            cnt2 += 1
    if cnt == N :
        flg = 1
    elif flg == 0 :
        ans += 1
    elif (N-cnt) == cnt2 :
        ans = -1

print(ans)

Submission status: Accepted

Solution code:
import sys,time
def inp(): return int(sys.stdin.readline())
def inpl(): return list(map(int, sys.stdin.readline().split()))

def solve():
    start = time.time()

    N = inp()
    AA = [inpl() for _ in range(N)]
    itrs = [0]*N
    ans = cnt = 0

    while True:
        next = set()
        for x,itr in enumerate(itrs):
            if itr < N-1:
                t = AA[x][itr] - 1
                if AA[t][itrs[t]]-1 == x:
                    next.add(x)

        for n in next:
            itrs[n] += 1
            if itrs[n] == N-1:
                cnt += 1

        if len(next) == 0:
            for x in itrs:
                if x != N-1:
                    return -1
            return ans

        now = time.time() - start
        if now > 1.6:
            return N*(N-1)//2

        ans += 1

if __name__ == '__main__':
    print(solve())

Submission status: Accepted

Solution code:
import sys
def LI(): return [int(x) for x in sys.stdin.readline().split()]
def II(): return int(sys.stdin.readline())


from collections import deque

from copy import copy
#debug = True
debug = False

def dprint(*objects):
    if debug == True:
        print(*objects)
def main():
    N = II()
    a_mat = []
    for i in range(N):
        a_mat.append(deque(LI()))

    cnt = 0
    first_list = [a_list.popleft() for a_list in a_mat]
    nend = 0
    previous_match_list = list(range(N))
    while True:
        # この日に試合できる可能性リスト
        # 試合する人リスト
        match_list = []
        for i in previous_match_list:
            a_no = first_list[i]
            a = a_no-1
            no = i+1
            # 試合をするペアの要素を入れていく
            if first_list[a] == no:
                match_list.append(i)

        dprint(first_list, match_list)

        if len(match_list) == 0:
            print(-1)
            return

        previous_match_list = copy(match_list)

        # 試合をしたことを反映
        for i in match_list:
            if len(a_mat[i]) == 0:
                first_list[i] = 0
                nend += 1 # 終わった人
            else:
                next_no = a_mat[i].popleft()
                next = next_no - 1
                first_list[i] = next_no
                previous_match_list.append(next)

        previous_match_list = list(set(previous_match_list))

        dprint(match_list, previous_match_list)
        dprint("")
        # 一日経過
        cnt += 1

        # 終了判定
        if nend == N:
            break


    print(cnt)


main()

Submission status: Accepted

Solution code:
N = int(input())
A = [list(map(int, input().split())) for n in range(N)]
P = [0] * N


def get_num(i):
    return A[i][P[i]] - 1


def update(mem, K):
    for i in mem:
        P[i] += 1
        if P[i] == N - 1:
            K.remove(i)


def f():
    K = {i for i in range(N)}
    L = {i for i in range(N)}
    mem = set()
    for t in range(N * (N - 1) // 2 + 1):
        if len(K) == 0:
            return t

        for i in L:
            if i in mem:
                continue

            j = get_num(i)
            if j in mem:
                continue

            if i == get_num(j):
                mem.add(i)
                mem.add(j)

        if len(mem) == 0:
            return -1
        update(mem, K)
        L = K & mem
        mem.clear()

    return -2

print(f())

Submission status: Accepted

Solution code:
n = int(input())
a = [[] for i in range(n)]
for i in range(n):
    a[i] = list(map(int, input().split()))
    
ans = 0
nowlist = [a[i][0] for i in range(n)]
ans = 0
amap = [[0 for i in range(max(0,j))] for j in range(n+1)]
dokomade = [0 for i in range(n+1)]
todaylist = []
tomorrow = []

for i in range(n):
    i1 = min(nowlist[i],i+1)
    i2 = max(nowlist[i],i+1)
    amap[i2][i1] += 1
    if(amap[i2][i1]==2):
        todaylist.append([i1,i2])

#print(amap)

while(True):
    for i in range(len(todaylist)):
        i1=todaylist[i][0]
        i2=todaylist[i][1]
        dokomade[i1]+=1
        dokomade[i2]+=1
        if(dokomade[i1]<n-1):
            temp1=i1
            temp2=a[i1-1][dokomade[i1]]
            i3=max(temp1,temp2)
            i4=min(temp1,temp2)
            amap[i3][i4]+=1
            if(amap[i3][i4]==2):
                tomorrow.append([i3,i4])
        if(dokomade[i2]<n-1):
            temp1=i2
            temp2=a[i2-1][dokomade[i2]]
            i3=max(temp1,temp2)
            i4=min(temp1,temp2)
            amap[i3][i4]+=1
            if(amap[i3][i4]==2):
                tomorrow.append([i3,i4])
    
    ans += 1
    #print(dokomade)
    if(len(tomorrow)==0):
        if(sum(dokomade)!= n*(n-1)):
            ans = -1
        break
    todaylist = tomorrow
    tomorrow=[]
    
print(ans)

Submission status: Accepted

Solution code:
N = int(input())
A = []
for i in range(N):
  As = list(map(int, input().split()))
  As = list(reversed(list(map(lambda a: a-1, As))))
  A.append(As)
#print(A)
d = 0
n = 0
l = list(range(N))
while True:
  n2 = 0
  l2 = []
  s2 = set()
  for i in l:
    if A[i] == []:
      continue
    j = A[i][-1]
    if A[j] == []:
      continue
    if i in s2 or j in s2:
      continue
    if A[j][-1] == i:
      n += 1
      n2 += 1
      s2.add(i)
      s2.add(j)
      l2.append(i)
      l2.append(j)
      A[i].pop()
      A[j].pop()
  if n2 == 0:
    if n == N*(N-1)//2:
      break
    print(-1)
    exit()
  l = l2
  d += 1
print(d)

Submission status: Accepted

Solution code:
from collections import deque

N = int(input())
A = [list(map(int, input().split()))[::-1] for _ in range(N)]

# pop_count = 0
l = [[0 for _ in range(N+1)] for _ in range(N+1)]
day = 0
q = deque([(i+1, a.pop()) for i, a in enumerate(A)])

while q:
    day += 1
    r = deque()
    while q:
        p = q.popleft()
        # print(p)
        # if p == "m":
        #     q.append("m")
        #     day += 1
        #     continue
        x, y = p
        if x > y:
            x, y = y, x
        l[x][y] += 1
        if l[x][y] >= 2:
            l[x][y] -= 2
            if A[x-1]:
                r.append((x, A[x-1].pop()))
            if A[y-1]:
                r.append((y, A[y-1].pop()))
    q = r

if all(map(len, A)):
    print(-1)
else:
    print(day)

Submission status: Accepted

Solution code:
# -*- coding: utf-8 -*-
"""
Created on Sun Sep  1 21:55:48 2019

@author: Yamazaki Kenichi
"""


N = int(input())
A = [list(map(int,input().split())) for i in range(N)]

T = [0 for i in range(N)]
today = [True for i in range(N)]
yesterday = [i for i in range(N)]

ans = 0
counta = 0
while counta < N:
    today = set([])
    today_p = []
    for i in yesterday:
        if not i in today:
            vs = A[i][T[i]] - 1
            if A[vs][T[vs]] == i + 1 and not vs in today:
                T[i] += 1
                T[vs] += 1
                if T[i] == N - 1:
                    T[i] = 0
                    counta += 1
                if T[vs] == N - 1:
                    T[vs] = 0 
                    counta += 1
                today.add(i)
                today.add(vs)
                today_p.extend([i,vs])
    yesterday = today_p
#        print(i,vs,today,T)
    if len(today_p) == 0:
        ans = -1
        break
    ans += 1
print(ans)

Submission status: Accepted

Solution code:
import sys
input = sys.stdin.readline
from collections import deque
def main():
    N = int( input())
    A = [deque()] + [deque( map( int, input().split())) for _ in range(N)]
    Days = [0]*(N+1)
    NOW = [0]*(N+1)
    # for i in range(1, N+1):
    #     a = A[i].popleft()
    #     if NOW[a] == i:
    #         Days[a] = Days[i] = max(Days[a], Days[i])
    q = deque( [ i+1 for i in range(N)])
    while q:
        i = q.popleft()
        if not A[i]:
            continue
        a = A[i].popleft()
        if NOW[a] == i:
            Days[a] = Days[i] = max(Days[a], Days[i])+1
            q.append(i)
            q.append(a)
            NOW[a] = NOW[i] = 0
        else:
            NOW[i] = a
    for i in range(1,N+1):
        if A[i]:
            print(-1)
            return
    print( max(Days))
if __name__ == '__main__':
    main()

Submission status: Accepted

Solution code:
# -*- coding: utf-8 -*-
import bisect
import heapq
import math
import random
import sys
from collections import Counter, defaultdict, deque
from decimal import ROUND_CEILING, ROUND_HALF_UP, Decimal
from functools import lru_cache, reduce
from itertools import combinations, combinations_with_replacement, product, permutations
from operator import add, mul, sub

sys.setrecursionlimit(100000)
input = sys.stdin.readline


def read_int():
    return int(input())


def read_int_n():
    return list(map(int, input().split()))


def read_float():
    return float(input())


def read_float_n():
    return list(map(float, input().split()))


def read_str():
    return input().strip()


def read_str_n():
    return list(map(str, input().split()))


def error_print(*args):
    print(*args, file=sys.stderr)


def mt(f):
    import time

    def wrap(*args, **kwargs):
        s = time.time()
        ret = f(*args, **kwargs)
        e = time.time()

        error_print(e - s, 'sec')
        return ret

    return wrap


@mt
def slv(N, A):
    ans = 0
    A = [list(reversed(a)) for a in A]

    s1 = set()
    s2 = set()
    for i in range(1, N+1):
        if A[i-1]:
            d = A[i-1][-1]
            n = (min(i, d), max(i, d))
            if n not in s1:
                s1.add(n)
            else:
                s2.add(n)
                s1.remove(n)
        
    while True:
        c = 0
        dell = []
        adding = []
        for k in s2:
            a, b = k
            A[a-1].pop()
            if A[a-1]:
                d = A[a-1][-1]
                n = (min(a, d), max(a, d))
                adding.append(n)
            A[b-1].pop()
            if A[b-1]:
                d = A[b-1][-1]
                n = (min(b, d), max(b, d))
                adding.append(n)
            dell.append(k)
            c += 1

        for k in dell:
            s2.remove(k)
        for k in adding:
            if k in s1:
                s2.add(k)
                s1.remove(k)
            else:
                s1.add(k)

        if c == 0:
            break
        else:
            ans += 1


    for a in A:
        if a:
            return -1
    return ans


def main():
    N = read_int()
    A = [read_int_n() for _ in range(N)]
    print(slv(N, A))

    # N = 1000
    # A = []

    # while True:
    #     for i in range(1, N+1):
    #         t = list(range(1, N+1))
    #         t.remove(i)
    #         random.shuffle(t)
    #         A.append(t)
    #     print(slv(N, A))


if __name__ == '__main__':
    main()