// https://infoarena.ro/problema/dfs
use std::{
collections::*, fmt::*, fs::{write, *}, mem::*, str::*
};
fn split_in_x_var<T: FromStr>(string: &str) -> Vec<T> where T::Err: Debug {
string.split_whitespace().map(|x| x.parse::<T>().unwrap()).collect::<Vec<T>>()
}
fn split_in_x<const N: usize, T: FromStr + Debug>(string: &str) -> [T; N] where T::Err: Debug {
string.split_whitespace().map(|x| x.parse::<T>().unwrap()).collect::<Vec<T>>().try_into().unwrap()
}
fn find_exista(componente_conexe: &mut Vec<HashSet<usize>>, muchie: usize) -> Option<usize> {
for (i, componenta_conexa) in componente_conexe.iter().enumerate() {
if componenta_conexa.contains(&muchie) {
return Some(i);
}
}
None
}
fn main() {
let content = read_to_string("dfs.in").unwrap();
let mut lines = content.lines();
let [noduri, _muchii]: [usize; 2] = split_in_x(lines.next().unwrap());
// let mut componente_conexe = vec![];
// let mut nr_componente_conexe = noduri;
// for line in lines {
// let [muchie1, muchie2]: [usize; 2] = split_in_x(line);
// let index1 = find_exista(&mut componente_conexe, muchie1);
// let index2 = find_exista(&mut componente_conexe, muchie2);
// match (index1, index2) {
// (Some(mut x), Some(mut y)) => {
// if x == y {
// continue;
// }
// if y < x {
// swap(&mut x, &mut y);
// }
// let other = componente_conexe.remove(y);
// componente_conexe[x].extend(other);
// }
// (Some(x), None) => {
// componente_conexe[x].insert(muchie2);
// }
// (None, Some(y)) => {
// componente_conexe[y].insert(muchie1);
// }
// (None, None) => {
// componente_conexe.push(HashSet::from([muchie1, muchie2]));
// }
// }
// nr_componente_conexe -= 1;
// }
// write("dfs.out", nr_componente_conexe.to_string()).unwrap();
}