# Union Find

def find(x):

    if par[x] < 0:

        return x

    else:

        par[x] = find(par[x])

        return par[x]





def unite(x, y):

    x = find(x)

    y = find(y)



    if x == y:

        return False

    else:

        if par[x] > par[y]:

            x, y = y, x

        par[x] += par[y]

        par[y] = x

        return True





def same(x, y):

    return find(x) == find(y)





def size(x):

    return -par[find(x)]





import sys



input = sys.stdin.readline

n, m = list(map(int, input().split()))

a = set()

for _ in range(m):

    ab = sorted(map(int, input().split()))

    a.add((ab[0], ab[1]))

par = [-1] * n



for x, y in a:

    unite(x - 1, y - 1)



d = {}

for i in range(n):

    i = find(i)

    if i in d:

        d[i] += 1

    else:

        d[i] = 1

print((max(d.values())))
# Union Find

def find(x):

    if par[x] < 0:

        return x

    else:

        par[x] = find(par[x])

        return par[x]





def unite(x, y):

    x = find(x)

    y = find(y)



    if x == y:

        return False

    else:

        if par[x] > par[y]:

            x, y = y, x

        par[x] += par[y]

        par[y] = x

        return True





import sys



input = sys.stdin.readline

n, m = list(map(int, input().split()))

par = [-1] * n

a = set()

for _ in range(m):

    ab = sorted(map(int, input().split()))

    a.add((ab[0], ab[1]))



for x, y in a:

    unite(x - 1, y - 1)



print((-min(par)))
# Union Find
def find(x):
    if par[x] < 0:
        return x
    else:
        par[x] = find(par[x])
        return par[x]


def unite(x, y):
    x = find(x)
    y = find(y)
    if x == y:
        return False
    else:
        if par[x] > par[y]:
            x, y = y, x
        par[x] += par[y]
        par[y] = x
        return True


def same(x, y):
    return find(x) == find(y)


def size(x):
    return -par[find(x)]


import sys

input = sys.stdin.readline
n, m = list(map(int, input().split()))
a = set()
for _ in range(m):
    ab = sorted(map(int, input().split()))
    a.add((ab[0], ab[1]))
par = [-1] * n
for x, y in a:
    unite(x - 1, y - 1)
d = {}
for i in range(n):
    i = find(i)
    if i in d:
        d[i] += 1
    else:
        d[i] = 1
print((max(d.values())))

# Union Find
def find(x):
    if par[x] < 0:
        return x
    else:
        par[x] = find(par[x])
        return par[x]


def unite(x, y):
    x = find(x)
    y = find(y)
    if x == y:
        return False
    else:
        if par[x] > par[y]:
            x, y = y, x
        par[x] += par[y]
        par[y] = x
        return True


import sys

input = sys.stdin.readline
n, m = list(map(int, input().split()))
par = [-1] * n
a = set()
for _ in range(m):
    ab = sorted(map(int, input().split()))
    a.add((ab[0], ab[1]))
for x, y in a:
    unite(x - 1, y - 1)
print((-min(par)))

-def same(x, y): -    return find(x) == find(y) - - -def size(x): -    return -par[find(x)] - - +par = [-1] * n -par = [-1] * n -d = {} -for i in range(n): -    i = find(i) -    if i in d: -        d[i] += 1 -    else: -        d[i] = 1 -print((max(d.values()))) +print((-min(par)))