#include <bits/stdc++.h>
using namespace std;
const int oo = 1000000009;
const double eps = 1e-6;
const int mod = 1000000007;
const int mx = 100005;
class State {
 public:
  int x;
  pair<int, int> d;
  State(int _x, pair<int, int> _d) {
    x = _x;
    d = _d;
  }
  bool operator<(const State &s) const { return d > s.d; }
};
vector<pair<int, int> > adj[mx];
pair<int, int> dist[mx];
int adfasdfdsfds[mx], nextz[mx];
int n, m;
set<pair<int, int> > roads;
map<pair<int, int>, int> status;
int main() {
  scanf("%d %d", &n, &m);
  for (int i = 0; i < (m); ++i) {
    int a, b, z;
    scanf("%d %d %d", &a, &b, &z);
    adj[a].push_back(make_pair(b, 1 - z));
    adj[b].push_back(make_pair(a, 1 - z));
    roads.insert(make_pair(min(a, b), max(a, b)));
    status[make_pair(a, b)] = 1 - z;
    status[make_pair(b, a)] = 1 - z;
  }
  for (int i = 1; i <= (n); ++i) dist[i] = make_pair(oo, oo);
  priority_queue<State> pq;
  dist[1] = make_pair(0, 0);
  pq.push(State(1, dist[1]));
  while (!pq.empty()) {
    State cur = pq.top();
    pq.pop();
    if (cur.d > dist[cur.x]) continue;
    for (int i = 0; i < ((int)(adj[cur.x].size())); ++i) {
      int y = adj[cur.x][i].first;
      pair<int, int> nxt(1 + cur.d.first, adj[cur.x][i].second + cur.d.second);
      if (nxt < dist[y]) {
        dist[y] = nxt;
        adfasdfdsfds[y] = cur.x;
        nextz[y] = adj[cur.x][i].second;
        pq.push(State(y, nxt));
      }
    }
  }
  vector<pair<pair<int, int>, int> > ans;
  int cur = n;
  while (cur != 1) {
    int nxt = adfasdfdsfds[cur];
    if (nextz[cur]) {
      ans.push_back(make_pair(make_pair(cur, nxt), 1));
    }
    roads.erase(roads.find(make_pair(min(cur, nxt), max(cur, nxt))));
    cur = nxt;
  }
  for (auto r : roads)
    if (!status[r]) {
      ans.push_back(make_pair(r, 0));
    }
  printf("%d\n", (int)(ans.size()));
  for (int i = 0; i < ((int)(ans.size())); ++i)
    printf("%d %d %d\n", ans[i].first.first, ans[i].first.second,
           ans[i].second);
  return 0;
}
