#include <bits/stdc++.h>
using namespace std;

#define eb emplace_back
#define INF 1LL<<62
#define FLT_INF pow(10.0, 16)

using ll = long long;
using vll = vector<ll>;
using ull = unsigned long long;
using int2 = pair<int, int>;

template <typename A> string to_string(const A& v);
string to_string(const string& s) { return '"'+ s + '"'; }
string to_string(const char *s) { return to_string((string)s); }
string to_string(bool b) { return (b ? "true" : "false"); }

template <typename A, typename B> string to_string(const pair<A, B>& p) {
  return "(" + to_string(p.first) + ", " + to_string(p.second) + ")";
}

template <typename A> string to_string(const A& v) {
  bool first = true;
  string res = "{";
  for (const auto &x : v) {
    if (!first) {
      res += ", ";
    }
    first = false;
    res += to_string(x);
  }
  res += "}";
  return res;
}

template <typename T>
void sort(vector<T>& val) {
  sort(val.begin(), val.end());
}

template <typename T>
void sort_b(vector<T>& val) {
  sort(val.begin(), val.end(), greater<T>());
}

void debug_out() { cerr << endl; }

template <typename Head, typename... Tail> void debug_out(Head H, Tail... T) {
  cerr << " " << to_string(H);
  debug_out(T...);
}

#ifdef LOCAL
#define debug(...) cerr << "[" << #__VA_ARGS__ << "]:", debug_out(__VA_ARGS__)
#else
#define debug(...);
#endif

#define COMMON_MOD pow(10, 9) + 7
#define PI 3.14159265

// sort(a.begin(), a.end(), less<ll>()); greater<ll>()
// cout<<fixed<<setprecision(20)<<(s/kl)*2;

void color_edges(const vector<vector<pair<int, int>>>& edges, int current_vert, vll& used_vertices, vll& vert_colors) {
  for (auto& edge: edges[current_vert]) {
    if (used_vertices[edge.first] == 1) {
      continue;
    }
    used_vertices[edge.first] = 1;
    if (edge.second % 2 == 0) {
      vert_colors[edge.first] = vert_colors[current_vert];
    } else {
      vert_colors[edge.first] = (vert_colors[current_vert] + 1) % 2;
    }
    color_edges(edges, edge.first, used_vertices, vert_colors);

  }

}

void mark_component(const vector<vll>& edges, int current_vert, vll& components, int comp_num) {
  for (int edge: edges[current_vert]) {
    if (components[edge] != 0) {
      continue;
    }
    components[edge] = comp_num;
    mark_component(edges, edge, components, comp_num);
  }

}

int main() {

  ios::sync_with_stdio(false);
  cin.tie(0);

  ll n, m;
  cin >> n >> m;

  vector<vll> edges(n, vll());

  for (int i = 0; i < m; i++) {
    ll x, y, z;
    cin >> x >> y >> z;
    x--;
    y--;
    edges[x].eb(y);
    edges[y].eb(x);
  }

  vll components(n, 0);
  ll comp_num = 1;
  for (int i = 0; i < n; i++) {
    if (components[i] == 0) {
      mark_component(edges, i, components, comp_num);
      comp_num++;
    }
  }
  cout << (comp_num-1);
  //ll n;
  // cin >> n;
  //
  // if (n == 1) {
  //   cout << 0 << endl;
  //   return 0;
  // }
  //
  // vector<vector<pair<int, int>>> edges(n, vector<pair<int, int>>());
  // for (int i = 0; i < n - 1; i++ ) {
  //   int u, v, w;
  //   cin >> u >> v >> w;
  //   u--;
  //   v--;
  //   edges[u].push_back({v, w});
  //   edges[v].push_back({u, w});
  // }
  //
  // vll vert_colors(n, 0);
  // vll used_vertices(n, 0);
  //
  //
  // for (int i = 0; i < n; i++) {
  //   if (used_vertices[i] == 0) {
  //     used_vertices[i] = 1;
  //     vert_colors[i] = 0;
  //     color_edges(edges, i, used_vertices, vert_colors);
  //   }
  // }
  //
  //
  //
  // for (int i = 0; i < n; i++) {
  //   cout << vert_colors[i] << endl;
  // }
  //


  //debug(edges);


  cout << endl;
  return 0;
}


Measured memory_bytes: 12800