Problem:
Score : 400 points

Problem Statement

There are N persons called Person 1 through Person N.

You are given M facts that "Person A_i and Person B_i are friends." The same fact may be given multiple times.

If X and Y are friends, and Y and Z are friends, then X and Z are also friends. There is no friendship that cannot be derived from the M given facts.

Takahashi the evil wants to divide the N persons into some number of groups so that every person has no friend in his/her group.

At least how many groups does he need to make?

Constraints

2 \leq N \leq 2\times 10^5

0 \leq M \leq 2\times 10^5

1\leq A_i,B_i\leq N

A_i \neq B_i

Input

Input is given from Standard Input in the following format:

N M
A_1 B_1
\vdots
A_M B_M

Output

Print the answer.

Sample Input 1

5 3
1 2
3 4
5 1

Sample Output 1

3

Dividing them into three groups such as \{1,3\}, \{2,4\}, and \{5\} achieves the goal.

Sample Input 2

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

Sample Output 2

4

Sample Input 3

10 4
3 1
4 1
5 9
2 6

Sample Output 3

3

Solution in Go (1.14.1) (judge verdict: Accepted)

package main

import (
    "bufio"
    "fmt"
    "os"
)

func generated_alib_swap(a int, b int) (int, int) {
    return b, a
}
func (u generated_alib_UnionFind) Size(x int) int {
    return -u.par[u.Find(x)]
}
func (u generated_alib_UnionFind) Union(x, y int) {
    xr := u.Find(x)
    yr := u.Find(y)
    if xr == yr {
        return
    }
    if u.Size(yr) < u.Size(xr) {
        yr, xr = generated_alib_swap(yr, xr)
    }
    u.par[yr] += u.par[xr]
    u.par[xr] = yr
}
func (u generated_alib_UnionFind) Find(x int) int {
    if u.par[x] < 0 {
        return x
    }
    u.par[x] = u.Find(u.par[x])
    return u.par[x]
}
func generated_alib_NewUnionFind(N int) *generated_alib_UnionFind {
    u := new(generated_alib_UnionFind)
    u.par = make([]int, N)
    for i := range u.par {
        u.par[i] = -1
    }
    return u
}

type generated_alib_UnionFind struct{ par []int }

func main() {
    r := bufio.NewReader(os.Stdin)
    w := bufio.NewWriter(os.Stdout)
    defer w.Flush()
    var n, m int
    fmt.Fscan(r, &n, &m)
    uf := generated_alib_NewUnionFind(n)
    for i := 0; i < m; i++ {
        var a, b int
        fmt.Fscan(r, &a, &b)
        a--
        b--
        uf.Union(a, b)
    }
    ans := 0
    for i := 0; i < n; i++ {
        if ans < uf.Size(i) {
            ans = uf.Size(i)
        }
    }
    fmt.Fprintln(w, ans)
}
/* this code was generated by the code below
package main

import (
   "bufio"
   "fmt"
   "os"

  alib "a/lib"
)

func main() {
   r := bufio.NewReader(os.Stdin)
   w := bufio.NewWriter(os.Stdout)
   defer w.Flush()

   var n, m int
   fmt.Fscan(r, &n, &m)
   uf := alib.NewUnionFind(n)

   for i := 0; i < m; i++ {
       var a, b int
       fmt.Fscan(r, &a, &b)
       a--
       b--

       uf.Union(a, b)
   }

   ans := 0
   for i := 0; i < n; i++ {
       if ans < uf.Size(i) {
           ans = uf.Size(i)
       }
   }

   fmt.Fprintln(w, ans)
}

*/