Problem:


Score : 700 points

Problem Statement

Takahashi is hosting an sports meet.
There are N people who will participate. These people are conveniently numbered 1 through N.
Also, there are M options of sports for this event. These sports are numbered 1 through M.
Among these options, Takahashi will select one or more sports (possibly all) to be played in the event.

Takahashi knows that Person i's j-th favorite sport is Sport A_{ij}.
Each person will only participate in his/her most favorite sport among the ones that are actually played in the event, and will not participate in the other sports.

Takahashi is worried that one of the sports will attract too many people.
Therefore, he would like to carefully select sports to be played so that the number of the participants in the sport with the largest number of participants is minimized.
Find the minimum possible number of the participants in the sport with the largest number of participants.

Constraints

1 \leq N \leq 300

1 \leq M \leq 300

A_{i1} , A_{i2} , ... , A_{iM} is a permutation of the integers from 1 to M.

Input

Input is given from Standard Input in the following format:

N M
A_{11} A_{12} ... A_{1M}
A_{21} A_{22} ... A_{2M}
:
A_{N1} A_{N2} ... A_{NM}

Output

Print the minimum possible number of the participants in the sport with the largest number of participants.

Sample Input 1

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

Sample Output 1

2

Assume that Sports 1, 3 and 4 are selected to be played. In this case, Person 1 will participate in Sport 1, Person 2 in Sport 3, Person 3 in Sport 3 and Person 4 in Sport 4.
Here, the sport with the largest number of participants is Sport 3, with two participants.
There is no way to reduce the number of participants in the sport with the largest number of participants to 1. Therefore, the answer is 2.

Sample Input 2

3 3
2 1 3
2 1 3
2 1 3

Sample Output 2

3

Since all the people have the same taste in sports, there will be a sport with three participants, no matter what sports are selected.
Therefore, the answer is 3.



Sample input:
4 5
5 1 3 4 2
2 5 3 1 4
2 3 1 4 5
2 5 4 3 1


Sample output:
2

Submission status: Accepted

Solution code:
from collections import deque
from typing import Optional


class DeletableDeque:
    """Deletable Deque: a deque that supports lazy deletion of values."""

    __slots__ = ["_set", "_deque"]

    def __init__(self, *initial_values: int) -> None:
        self._set = set()
        self._deque = deque([])

        if initial_values:
            for v in initial_values:
                self.append(v)

    def __contains__(self, value: int) -> bool:
        return value in self._set

    def __len__(self) -> int:
        return len(self._set)

    @property
    def is_empty(self) -> bool:
        """Return whether the deque has no values or not."""
        return len(self) == 0

    @property
    def top(self) -> Optional[int]:
        """Return the rightmost value from the deque.
        If the deque is empty, None is returned.
        """
        while self._deque and self._deque[-1] not in self._set:
            self._deque.pop()
        if not self._deque:
            return None
        return self._deque[-1]

    @property
    def topleft(self) -> Optional[int]:
        """Return the leftmost value from the deque.
        If the deque is empty, None is returned.
        """
        while self._deque and self._deque[0] not in self._set:
            self._deque.popleft()
        if not self._deque:
            return None
        return self._deque[0]

    def pop(self) -> Optional[int]:
        """Pop and return the rightmost value from the deque.
        If the deque is empty, None is returned.
        """
        while self._deque and self._deque[-1] not in self._set:
            self._deque.pop()
        if not self._deque:
            return None
        res = self._deque.pop()
        self._set.discard(res)
        return res

    def popleft(self) -> Optional[int]:
        """Pop and return the leftmost value from the deque.
        If the deque is empty, None is returned.
        """
        while self._deque and self._deque[0] not in self._set:
            self._deque.popleft()
        if not self._deque:
            return None
        res = self._deque.popleft()
        self._set.discard(res)
        return res

    def append(self, value: int) -> None:
        """Append value to the right side of the deque."""
        if value in self._set:
            return
        self._set.add(value)
        self._deque.append(value)

    def appendleft(self, value: int) -> None:
        """Append value to the left side of the deque."""
        if value in self._set:
            return
        self._set.add(value)
        self._deque.appendleft(value)

    def delete(self, value: int) -> None:
        """Delete value from the deque."""
        if value not in self._set:
            return
        self._set.discard(value)


def agc018_b():
    # https://atcoder.jp/contests/agc018/tasks/agc018_b
    import sys
    from collections import defaultdict

    readline = sys.stdin.buffer.readline

    N, M = map(int, readline().split())
    A = [DeletableDeque(*map(int, readline().split())) for _ in range(N)]

    res = 301
    for _ in range(M):
        cnt = defaultdict(int)
        for a in A:
            cnt[a.topleft] += 1

        popular_sport = max(cnt, key=cnt.get)
        res = min(res, cnt[popular_sport])
        for a in A:
            a.delete(popular_sport)

    print(res)


if __name__ == "__main__":
    agc018_b()

Submission status: Accepted

Solution code:
import collections

N, M = map(int, input().split())
A = [list(map(int, input().split())) for i in range(N)]
ans = N  # １種類だけ開催

s = set()
for _ in range(M-1):
    count = [0]*M
    for i in range(N):
        for x in A[i]:
            if x in s:
                continue
            else:
                count[x-1] += 1
                break
    ans = min(ans, max(count))
    idx = count.index(max(count))
    s.add(idx + 1)

print(ans)

Submission status: Accepted

Solution code:
n, m = map(int, input().split())
a = [list(map(int, input().split())) for i in range(n)]
for i in range(n):
    a[i].reverse()

ans = n
used = set()
for i in range(m):
    count = [0]*(m+1)
    for j in range(n):
        count[a[j][-1]] += 1

    ans = min(max(count), ans)
    num = count.index(max(count))
    used.add(num)
    for j in range(n):
        while len(a[j]) > 0:
            if a[j][-1] in used:
                a[j].pop()
            else:
                break

print(ans)

Submission status: Accepted

Solution code:
import bisect
import copy
import heapq
import math
import sys
from collections import *
from functools import lru_cache
from itertools import accumulate, combinations, permutations, product
def input():
    return sys.stdin.readline()[:-1]
def ruiseki(lst):
    return [0]+list(accumulate(lst))
sys.setrecursionlimit(500000)
mod=pow(10,9)+7
al=[chr(ord('a') + i) for i in range(26)]
direction=[[1,0],[0,1],[-1,0],[0,-1]]

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


def check(dic):
    lst=[0]*m
    for i in range(n):
        for j in range(m):
            if dic[a[i][j]]==1:
                lst[a[i][j]-1]+=1
                break
    maxl=max(lst)
    # print(dic,maxl,lst)
    if maxl==0:
        return n
    for i in range(m):
        if lst[i]==maxl:
            dic[i+1]=0
            break

    return min(maxl,check(dic))


dic={}
for i in range(m):
    dic[i+1]=1
# print(dic)
print(check(dic))

Submission status: Accepted

Solution code:
n,m = map(int,input().split())
a = tuple([tuple(map(int,input().split())) for _ in range(n)])

ok = n
ng = 0
for _ in range(10):
    mid = (ok+ng)//2

    check = True
    inds = [0] * n
    done = [0] * (m+1)
    while(check):
        cnt_max = 0
        cnt = [0] * (m+1)
        for i in range(n):
            ind = inds[i]
            while(done[a[i][ind]] != 0):
                ind += 1
                if(ind == m):
                    check = False
                    break
            if(ind < m):
                inds[i] = ind
                cnt[a[i][ind]] += 1
                cnt_max = max(cnt_max, cnt[a[i][ind]])

        if(cnt_max <= mid):
            break

        for i in range(1,m+1):
            if(cnt[i] > mid):
                done[i] = 1

    if(check):
        ok = mid
    else:
        ng = mid

print(ok)

Submission status: Accepted

Solution code:
import sys
import numpy as np

read = sys.stdin.buffer.read
readline = sys.stdin.buffer.readline
readlines = sys.stdin.buffer.readlines

N, M = map(int, readline().split())
A = np.array(read().split(), np.int64)

A = A.reshape(N, M)

def f(A):
    if A.shape[1] == 0:
        return 10**9
    count = np.bincount(A[:, 0])
    n = count.max()
    i = count.argmax()
    A = A.ravel()
    A = A[A != i]
    A = A.reshape(N, -1)
    return min(n, f(A))

print(f(A))

Submission status: Accepted

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

def solve(bans):
    cnts=[0]*m
    for itm in a:
        for fav in itm:
            if (fav-1) in bans:
                continue
            cnts[fav-1]+=1
            break
    ret = max(cnts)
    max_ss = [i for i, v in enumerate(cnts) if v == ret]
    return ret, max_ss # current ans, most popular sports

ban_s = []
ans=10000
while True:
    ret, max_ss = solve(ban_s)
    if ret==0:
        break
    ans=min(ans,ret)
    ban_s.extend(max_ss)

print(ans)

Submission status: Accepted

Solution code:
from numpy import*
n=x=len(a:=loadtxt(open(0),"i",skiprows=1,ndmin=2))
while any(a):x=min(x,max(t:=bincount(a[:,0])));a=reshape(a[a!=argmax(t)],(n,-1))
print(x)

Submission status: Accepted

Solution code:
from collections import*
(n,m),*d=[list(map(int,o.split()))for o in open(0)]
r=range(a:=n)
for _ in[0]*m:
 k=[]
 for i in r:k+=d[i][0],
 I,w=Counter(k).most_common()[0];a=min(a,w)
 for j in r:d[j].remove(I)
print(a)

Submission status: Accepted

Solution code:
from numpy import*
n=x=len(a:=loadtxt(open(0),"i",skiprows=1,ndmin=2))
while a.any():x=min(x,max(t:=bincount(a[:,0])));a=reshape(a[a!=argmax(t)],(n,-1))
print(x)

Submission status: Accepted

Solution code:
n,m=map(int,input().split())
#n人が参加<=300
#m個のスポーツ<=300
#最も多くの人が参加しているスポーツの最小

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

a=[[-1]*m for _ in range(n)]

for y in range(n):
    for x in range(m):
        a[y][aa[y][x]-1]=x

def pri(x):
    for item in x:
        print(item)

ans=301
for _ in range(m):
    score=[0]*m
    #print("###########")
    #pri(a)
    for y in range(n):
        mini=-1
        miniscore=501
        for x in range(m):
            if miniscore>a[y][x]:
                mini=x
                miniscore=a[y][x]
        score[mini]+=1
    tmp=max(score)
    ans=min(tmp,ans)
    #print(score)
    for x in range(m):
        if score[x]==tmp:
            for y in range(n):
                a[y][x]=501

print(ans)

Submission status: Accepted

Solution code:
#!/usr/bin/env python3
from collections import Counter
(n, m), *d = [list(map(int, o.split())) for o in open(0)]
a = n
for _ in [0] * m:
    k = []
    for i in range(n):
        k += d[i][0],
    ind, w = Counter(k).most_common()[0]
    a = min(a, w)
    for j in range(n):
        d[j].remove(ind)
print(a)

Submission status: Accepted

Solution code:
# Sports Festival
from collections import Counter
N, M = map(int, input().split())
data = [list(map(int, input().split())) for i in range(N)]
ans = N
for i in range(M):
    K = []
    for j in range(N):
        K.append(data[j][0])
    index, weight = Counter(K).most_common()[0]
    ans = min(ans, weight)
    for k in range(N):
        data[k].remove(index)
print(ans)

Submission status: Accepted

Solution code:
from collections import defaultdict
N, M = map(int, input().split())
A = [list(map(int, input().split())) for _ in range(N)]

hold = defaultdict(list)
like = [0] * N
sport = 0
NG = [False] * (M + 1)
ans = []

while all(like[i] < M for i in range(N)):
    hold = defaultdict(list)
    for i in range(N):
        hold[A[i][like[i]]].append(i)

    res = -1
    for k, v in hold.items():
        if len(v) > res:
            res = len(v)
            sport = k
    NG[sport] = True
    ans.append(res)

    for i in range(N):
        while like[i] < M:
            if NG[A[i][like[i]]]:
                like[i] += 1
            else:
                break

print(min(ans))

Submission status: Accepted

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

s = set()
indices = [0] * N
nums = dict(zip(range(1, M+1), [[] for i in range(M)]))
nn, mm = 0, 0
for i, idx in enumerate(indices):
  m = A[i][idx]
  nums[m].append(i)
  if len(nums[m]) > nn:
    nn = len(nums[m])
    mm = m

ans = nn
for _ in range(M-1):
  s.add(mm)
  for i in nums[mm]:
    idx = indices[i] + 1
    m = A[i][idx]
    while m in s:
      idx += 1
      m = A[i][idx]
    indices[i] = idx
    nums[m].append(i)
  nums.pop(mm)
  nn = 0
  for k in nums:
    if len(nums[k]) > nn:
      nn = len(nums[k])
      mm = k
  ans = min(ans, nn)

print(ans)

Submission status: Accepted

Solution code:
n, m = map(int, input().split())
a = [list(map(int, input().split())) for _ in range(n)]
ans = 3000
t = [True] * m
for _ in range(m):
    p = [0] * m
    for i in range(n):
        for x in a[i]:
            if t[x - 1]:
                p[x - 1] += 1
                break
    ma = max(p)
    ans = min(ans, ma)
    t[p.index(ma)] = False
print(ans)

Submission status: Accepted

Solution code:
from collections import Counter
from operator import itemgetter
import sys
input = sys.stdin.readline

N, M = map(int, input().split())
As = [list(map(int, input().split())) for _ in range(N)]
indices = [0 for i in range(N)] 
#i+1 th person attends his (indices[i]+1) th best favorite sport.

min_turnout = N
canceled_sports = set()
for _ in range(M-1):
    popular_sport, turnout = max(Counter(As[i][indices[i]] for i in range(N)).items(), key = itemgetter(1))
    min_turnout = min(min_turnout, turnout)
    canceled_sports.add(popular_sport)
    for i in range(N):
        while As[i][indices[i]] in canceled_sports:
            indices[i] += 1

print(min_turnout)

Submission status: Accepted

Solution code:
import bisect
import copy
import heapq
import sys
import itertools
import math
import queue
input = sys.stdin.readline
sys.setrecursionlimit(1000000)
# mod = 10 ** 9 + 7
mod = 998244353 

def read_values(): return map(int, input().split())
def read_index(): return map(lambda x: int(x) - 1, input().split())
def read_list(): return list(read_values())
def read_lists(N): return [read_list() for n in range(N)]
def init_dp1(init, N): return [init for _ in range(N)]
def init_dp2(init, N, M): return [[init for _ in range(M)] for _ in range(N)]


class V:
    def __init__(self, f, v=None):
        self.f = f
        self.v = v
 
    def __str__(self):
        return str(self.v)
 
    def ud(self, n):
        if n is None:
            return

        if self.v is None:
            self.v = n
            return
        self.v = self.f(self.v, n) 


def f(A, S):
    T = [0] * len(A[0])
    for a in A:
        for k in a:
            if k in S:
                continue
            T[k] += 1
            break
    
    v = max(T)
    return (T.index(v), v)


def main():
    N, M = read_values()
    A = [list(read_index()) for _ in range(N)]

    K = [0] * N

    res = V(min, N)
    S = set()
    for _ in range(M - 1):
        k, v = f(A, S)
        S.add(k)
        res.ud(v)

    print(res)


if __name__ == "__main__":
    main()

Submission status: Accepted

Solution code:
import bisect
import copy
import heapq
import sys
import itertools
import math
import queue
input = sys.stdin.readline
sys.setrecursionlimit(1000000)
# mod = 10 ** 9 + 7
mod = 998244353 

def read_values(): return map(int, input().split())
def read_index(): return map(lambda x: int(x) - 1, input().split())
def read_list(): return list(read_values())
def read_lists(N): return [read_list() for n in range(N)]
def init_dp1(init, N): return [init for _ in range(N)]
def init_dp2(init, N, M): return [[init for _ in range(M)] for _ in range(N)]


class V:
    def __init__(self, f, v=None):
        self.f = f
        self.v = v
 
    def __str__(self):
        return str(self.v)
 
    def ud(self, n):
        if n is None:
            return

        if self.v is None:
            self.v = n
            return
        self.v = self.f(self.v, n) 


def f(A, S):
    T = [0] * len(A[0])
    for a in A:
        for k in a:
            if k in S:
                continue
            T[k] += 1
            break
    
    v = max(T)
    return (T.index(v), v)


def main():
    N, M = read_values()
    A = [list(read_index()) for _ in range(N)]

    res = V(min, N)
    S = set()
    for _ in range(M - 1):
        k, v = f(A, S)
        S.add(k)
        res.ud(v)

    print(res)


if __name__ == "__main__":
    main()

Submission status: Accepted

Solution code:
from collections import deque, Counter
n, m = map(int, input().split())

cnt = Counter()
ques = []
for _ in range(n):
    a = list(map(int, input().split()))
    cnt[a[0]] += 1
    ques.append(deque(a))

ans = n
used = [False for _ in range(m+1)]
while True:
    cnt_most = cnt.most_common()
    if cnt_most[0][1] == 0:
        break
    ans = min(ans, cnt_most[0][1])
    for x, t in cnt_most:
        if t >= ans:
            used[x] = True
        else:
            break
    for i in range(n):
        while len(ques[i]) > 0 and used[ques[i][0]]:
            x = ques[i].popleft()
            cnt[x] -= 1
            if len(ques[i]) > 0:
                cnt[ques[i][0]] += 1

print(ans)

Submission status: Accepted

Solution code:
from collections import defaultdict
con = 10 ** 9 + 7; INF = float("inf")

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

#処理内容
def main():
	N, M = getlist()
	D = defaultdict(lambda:1)
	A = []
	for i in range(N):
		a = list(reversed(getlist()))
		A.append(a)

	if M == 1:
		print(N)
		return

	ans = INF
	for i in range(M - 1):
		cnt = [0] * M
		for j in range(N):
			cnt[A[j][-1] - 1] += 1

		# print(cnt)

		var = max(cnt)
		ans = min(ans, var)
		ind = cnt.index(var)
		D[ind] = 0
		for j in range(N):
			while True:
				if D[A[j][-1] - 1] == 0:
					A[j].pop()
				else:
					break

	print(ans)

if __name__ == '__main__':
	main()

Submission status: Accepted

Solution code:
import sys
input = sys.stdin.readline

def pop_ind(ind, n):
    for i in range(n):
        A[i].remove(ind)

def count(m):
    counter = [0] * (m+1)
    ind = -1
    max_cnt = 0
    for i in range(N):
        counter[A[i][0]] += 1
        if counter[A[i][0]] > max_cnt:
            max_cnt = counter[A[i][0]]
            ind = A[i][0]
    return ind, max_cnt

N, M = map(int, input().split())
A = [list(map(int, input().split())) for _ in range(N)]
ans = float('inf')
for _ in range(M):
    ind, tmp = count(M)
    pop_ind(ind, N)
    ans = min(ans, tmp)
print(ans)

Submission status: Accepted

Solution code:
N,M=map(int,input().split())

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

now=[0]*N
is_hold=[1]*M

ans=10**9
for _ in range(M):
    sanka=[0]*M
    for i in range(N):
        #print(A[i])
        sanka[A[i][now[i]]-1]+=1
    
    temp=max(sanka)
    ans=min(ans,temp)
    #print(ans)
    for i in range(len(sanka)):
        if sanka[i]==temp:
            tgt=i
            break
    is_hold[tgt]=0
    #print(is_hold)
    
    if _ == M-1:
        break
    for i in range(N):
        #print(i)
        while is_hold[A[i][now[i]]-1]==0:
            #print(i,now[i])
            now[i]+=1
        
print(ans)

Submission status: Accepted

Solution code:
# -*- coding: utf-8 -*-
"""
Created on Wed Apr 29 22:05:28 2020
"""

import sys
#import numpy as np

sys.setrecursionlimit(10 ** 9)
#def input():
#    return sys.stdin.readline()[:-1]
mod = 10**9+7

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


#s = [0 for _ in range(M+1)]
p = [0 for _ in range(N)]
un_held = set([])
ans = M + 10**3

while len(un_held) < M:
    s = [0 for _ in range(M+1)]
    for i in range(N):
        s[A[i][p[i]]] += 1
    tmp = 0
    for j in range(1,M+1):
        if s[j] > tmp:
            tmp = s[j]
            un = j
    ans = min(tmp,ans)
    un_held.add(un)
    for i in range(N):
        while p[i] < M and A[i][p[i]] in un_held:
            p[i] += 1
    #s[un] = 0
#    print(ans,un_held)
#    print(s)
#    print(p)

print(ans)

Submission status: Accepted

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

pointer={i:0 for i in range(0,N)}
cancel=set([])
ans=N
while True:
    dic={i:0 for i in range(1,M+1)}
    for i in range(0,N):
        dic[A[i][pointer[i]]]+=1
    most=max(dic[i] for i in range(1,M+1))
    ans=min(ans,most)
    for i in range(1,M+1):
        if dic[i]==most:
            cancel.add(i)

    for i in range(0,N):
        while A[i][pointer[i]] in cancel:
            pointer[i]+=1
            if pointer[i]==M:
                print(ans)
                exit()

Submission status: Accepted

Solution code:
from collections import defaultdict
N, M  = map(int, input().split())
li1 = []
li2 = []
for i in range(N):
    A = list(map(int, input().split()))
    li1.append(A)
U = 300
L = 0
while U-L > 1:
    m = (U+L)//2
    li = [0] * M
    flag = False
    while not flag:
        d = defaultdict(int)
        if not 0 in li:
            break
        for i in range(N):
            for j in range(M):
                if li[li1[i][j]-1] == 0:
                    d[li1[i][j]] += 1 #dのkeyは競技
                    break
        f = True
        for k in d:
            if d[k] > m:
                li[k-1] = 1
                f = False
        if f:
            flag = True
    if flag:
        U = m
    else:
        L = m
print(U)

Submission status: Accepted

Solution code:
from collections import deque, Counter
n,m = map(int,input().split())
ls = [deque(map(int,input().split())) for i in range(n)]
seen = [0 for i in range(m+1)]
content = [0 for i in range(n)]
flg = [0 for i in range(n)]
cnt = 0
ans = 500
for i in range(n):
  content[i] = ls[i][0]
c = Counter(content)
while cnt<m:
  for i in range(n):
    if flg[i]:
      while ls[i]:
        ls[i].popleft()
        if seen[ls[i][0]] >= 1:
          continue
        else:
          content[i] = ls[i][0]
          break
      flg[i] = 0
  c = Counter(content)
  x = c.most_common()[0]
  ans = min(ans,x[1])
  seen[x[0]] += 1
  for i in range(n):
    if content[i] == x[0]:
      flg[i] = 1
  cnt += 1
print(ans)

Submission status: Accepted

Solution code:
N, M = map(int, input().split())
A = [list(reversed(list(map(int, input().split())))) for _ in range(N)]

res = N
removed = [0 for _ in range(M)]

while not all(removed):
    S = [0 for _ in range(M)]
    for a in A:
        S[a[-1] - 1] += 1
    res = min(res, max(S))
    x = S.index(max(S))
    removed[x] = 1
    for a in A:
        while a and removed[a[-1] - 1]:
            a.pop()

print(res)

Submission status: Accepted

Solution code:
n,m = map(int,input().split())
a = []
for i in range(n):
    a0 = list(map(int,input().split()))
    a.append(a0)
l = [0 for i in range(m)]
d = []
kl = [0 for i in range(n)]
for i in range(n):
    l[a[i][0] - 1] += 1
for i in range(m):
    d.append([l[i],i])
d.sort(reverse=True)
ans = d[0][0]
for i in range(m-1):
    l[d[0][1]] = -1
    for i in range(n):
        #print(kl,l)
        if a[i][kl[i]]-1 == d[0][1]:
            while l[a[i][kl[i]]-1] < 0:
                kl[i] += 1
            l[a[i][kl[i]]-1] += 1
        #print(kl,l)
    d = []
    for i in range(m):
        if l[i] >= 0:
            d.append([l[i],i])
    d.sort(reverse=True)
    ans = min(ans,d[0][0])
print(ans)

Submission status: Accepted

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

N, M = map(int, input().split())
A = [list(map(int, input().split())) for _ in range(N)]
lb, ub = 0, N
while ub - lb > 1:
    m = (lb + ub) // 2
    idx = [0] * N
    not_use = set()
    ok = True
    while True:
        count = [0] * (M+1)
        for i in range(N):
            if idx[i] == -1:
                continue
            while idx[i] < M and A[i][idx[i]] in not_use:
                idx[i] += 1
            if idx[i] == M:
                ok = False
                break
            count[A[i][idx[i]]] += 1

        if not ok:
            break
        if max(count) <= m:
            break
        for i in range(1, M+1):
            if count[i] > m:
                not_use.add(i)
    if ok:
        ub = m
    else:
        lb = m
print(ub)

Submission status: Accepted

Solution code:
n,m=map(int,input().split())
a=[list(map(int,input().split())) for i in range(n)]
check=[1]*m
ans=n
for i in range(m):
  cnt=[0]*m
  for j in range(n):
    for k in range(m):
      if check[a[j][k]-1]:
        cnt[a[j][k]-1]+=1
        break
  if max(cnt)<ans:
    ans=max(cnt)
  check[cnt.index(max(cnt))]=0
print(ans)

Submission status: Accepted

Solution code:
# 写経AC
from collections import deque, defaultdict

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

def check(X):
    """
    最多参加のスポーツの参加人数がX以下になるか
    """
    # que[i]: 人iが参加したいスポーツ
    que = [deque() for _ in range(N)]
    # ng[j]: スポーツjはダメ
    ng = [False] * M
    for i in range(N):
        for j in range(M):
            que[i].append(A[i][j])
    
    while True:
        # cnt[j]: スポーツjに参加したい人数
        cnt = defaultdict(int)
        for i in range(N):
            cnt[que[i][0]] += 1

        # 定員over フラグ
        flag = False
        for s, c in cnt.items():
            if X < c:
                flag = True
                ng[s] = True

        # 参加人数が全てX以下
        if not flag:
            return True
        
        for i in range(N):
            # 参加したいスポーツがngの場合
            while que[i] and ng[que[i][0]]:
                que[i].popleft()
            # 参加できるスポーツがない場合
            if not que[i]:
                return False

def main():
    ng, ok = 0, N
    while ok - ng > 1:
        mid = (ng + ok) // 2
        if check(mid):
            ok = mid
        else:
            ng = mid
    print(ok)

if __name__ == "__main__":
    main()

Submission status: Accepted

Solution code:
import sys

read = sys.stdin.read
readline = sys.stdin.readline

N, M, *A = map(int, read().split())
A = list(map(list, map(reversed, zip(*[iter(A)] * M))))

# 各スポーツに参加している人数
p = [0] * (M + 1)
canceled = set()
answer = []


def solve(s, n):
    # nは開催しているスポーツの数
    # sは新たに開催をやめるスポーツ
    if n == 1:
        answer.append(N)
    elif n == M:
        for i in A:
            p[i[-1]] += 1
        p_max = max(p)
        answer.append(p_max)
        cancel = p.index(p_max)
        solve(cancel, n - 1)
    else:
        canceled.add(s)
        p[s] = 0
        for i in range(N):
            if A[i][-1] in canceled:
                while A[i][-1] in canceled:
                    A[i].pop()
                p[A[i][-1]] += 1
        p_max = max(p)
        answer.append(p_max)
        cancel = p.index(p_max)
        solve(cancel, n - 1)


solve(0, M)
print(min(answer))

Submission status: Accepted

Solution code:
import sys
input = sys.stdin.buffer.readline

def main():
    N,M = map(int,input().split())
    a = [list(map(int,input().split())) for _ in range(N)]
    
    def p(s):
        if all(s) == True:
            return 300
        al = [0 for _ in range(M)]
        for i in range(N):
            for j in a[i]:
                if not s[j-1]:
                    al[j-1] += 1
                    break
        count,index = max(al),al.index(max(al))
        s[index] = True
        return min(count,p(s))
    
    s = [False for _ in range(M)]
    print(p(s))

if __name__ == "__main__":
    main()

Submission status: Accepted

Solution code:
n,m=map(int,input().split())
l=[list(map(int,input().split())) for i in range(n)]
check=[1 for i in range(m)]
ans=n

for i in range(m):
  count=[0]*m
  for j in range(n):
    for k in range(m):
      if check[l[j][k]-1]==1:
        count[l[j][k]-1]+=1
        break
  if max(count)<ans:
    ans=max(count)
  check[count.index(max(count))]=0
print(ans)

Submission status: Accepted

Solution code:
n, m = map(int,input().split())
A = [list(map(int,input().split())) for i in range(n)]
for i in range(n):
    for j in range(m):
        A[i][j] -= 1
S = [0] * m
for i in range(n):
    S[A[i][0]] += 1

l = 0
r = n+1
mi = (l+r) // 2
while r-l>1:
    T = S[:]
    ng = 0
    I = [0] * n
    Y = [0] * m
    while ng == 0:
        M = [0] * m
        for i in range(m):
            if T[i] > mi:
                M[i] = 1
                Y[i] = 1
        # print(T,M)
        if sum(M) == 0:
            break
        for i in range(n):
            if M[A[i][I[i]]] == 1:
                T[A[i][I[i]]] -= 1
                while I[i] < m and Y[A[i][I[i]]] == 1:
                    I[i] += 1
                if I[i] == m:
                    ng = 1
                    break
                T[A[i][I[i]]] += 1
    if ng == 1:
        l = mi
    else:
        r = mi
    mi = (l+r) // 2
print(r)

Submission status: Accepted

Solution code:
N,M = map(int, input().split())
A = [[int(a) for a in input().split()] for _ in range(N)]

L = [0]*(M+1) #L[i]:0ならスポーツiを含める、1なら含めない
I = [0]*N #A[i][I[i]]:人iが参加するスポーツ
ans = N
flag = True
while flag:
    cnt = [0]*(M+1)
    for i in range(N):
        while I[i] < N and L[A[i][I[i]]] == 1:
            I[i] += 1
        if I[i] == N:
            flag = False
            break
        cnt[A[i][I[i]]] += 1
    if flag:
        num = max(cnt)
        ans = min(ans, num)
        for i in range(1, M+1):
            if cnt[i] == num:
                L[i] = 1
    if sum(L) == M:
        flag = False

print(ans)

Submission status: Accepted

Solution code:
#解説参照
import sys
input = sys.stdin.readline
n,m = map(int, input().split( ))
a = [list(map(int, input().split( ))) for _ in range(n)]

M = {i for i in range(1,m+1)}
cnt = [0]*(m+1)
cursor = [0]*n
for i in range(n):
    cnt[a[i][0]]+=1

q = max(cnt)
ans = q
p = cnt.index(q)
for _ in range(m):##qでは不足
    cnt[p]=0
    M.remove(p)
    for i in range(n):
        if a[i][cursor[i]]==p:
            while a[i][cursor[i]] not in M:
                cursor[i]+=1
                if cursor[i]==m:
                    print(ans)
                    exit()
            cnt[a[i][cursor[i]]]+=1
    q2 = max(cnt)
    ans = min(ans,q2)
    p = cnt.index(q2)
print(ans)

Submission status: Accepted

Solution code:
import collections

def judge(k):
  pos=[0]*n
  dic=collections.defaultdict(int)
  s=set()
  for i in range(n):
    dic[arr[i][0]]+=1
  while 1:
    key=list(dic.keys())
    for i in key:
      if dic[i]>k:
        s.add(i)
        del dic[i]
    flag=True
    for i in range(n):
      if arr[i][pos[i]] in s:
        flag=False
        pos[i]+=1
        if pos[i]==m:
          return False
        dic[arr[i][pos[i]]]+=1
    if flag==True:
      return True

n,m=map(int,input().split())
arr=[list(map(int,input().split())) for _ in range(n)]
l=0
r=n+1
while r-l!=1:
  mid=(l+r)//2
  if judge(mid)==True:
    r=mid
  else:
    l=mid
print(r)

Submission status: Accepted

Solution code:
n,m = map(int,input().split())
a = [list(map(int,input().split())) for _ in range(n)]
flag = [True for i in range(m+1)]
ans = n
for _ in range(m-1):
    cnt = [0 for i in range(m+1)]
    for i in range(n):
        for j in range(m):
            if flag[a[i][j]]:
                cnt[a[i][j]]+=1
                break
    t = 0
    cat = 0
    for i in range(m+1):
        if cnt[i]>t:
            cat = i
            t = cnt[i]
    ans = min(ans,t)
    flag[cat] = False
print(ans)