3 5
2 1 608591421 720962564
3 2 608591421 641991574
3 2 718110706 353409763
2 3 482786015 858341723
3 2 825397574 357507279
 2 1
2 1 317425595 636156322
 50000 1
20845 28516 904146168 997637433

Yes
641991574 1
2 
 Yes
0 0

 Yes
0 0


#include <bits/stdc++.h>
#pragma warning(disable : 4996)
using namespace std;
const int MAXV = 50011;
const int MAXE = 50011;
class EDGE {
 public:
  EDGE(int who, int c, int t, int i) : who(who), c(c), t(t), i(i) {}
  int who, c, t;
  int i;
};
bool echk[MAXE];
bool vchk[MAXV];
vector<EDGE> lst[MAXV], ll[MAXV];
map<int, int> cmap;
int ccnt = 0;
vector<pair<int, int> > clist[MAXE];
void dfs(int u, vector<EDGE>& elist) {
  for (auto e : ll[u]) {
    if (!echk[e.i]) {
      echk[e.i] = true;
      elist.push_back(e);
      dfs(e.who, elist);
    }
  }
}
class ELIST {
 public:
  ELIST(int a, int b, int odd, int even, vector<EDGE> elist)
      : a(a), b(b), odd(odd), even(even), elist(elist){};
  int a, b, odd, even;
  int eindex;
  vector<EDGE> elist;
};
vector<ELIST> odds, evens;
bool chk_evens[MAXV];
vector<int> egraph[MAXV], xgraph[MAXV];
bool pchk[MAXV];
bool chk(int a) { return vchk[a] || pchk[a]; }
int n;
int edeg[MAXV];
bool forceRun(ELIST& e, bool use_a, int m, vector<int>& Q, vector<int>* solist);
bool forceFor(int u, int m, vector<int>& Q, vector<int>* solist) {
  bool res = true;
  for (auto i : egraph[u]) {
    ELIST& e = evens[i];
    if (chk_evens[e.eindex]) continue;
    int v = e.a + e.b - u;
    res = res && forceRun(e, (e.a == v), m, Q, solist);
  }
  return res;
}
bool forceRun(ELIST& e, bool use_a, int m, vector<int>& Q,
              vector<int>* solist) {
  chk_evens[e.eindex] = true;
  edeg[e.a]--;
  edeg[e.b]--;
  if (edeg[e.a] == 1) Q.push_back(e.a);
  if (edeg[e.b] == 1) Q.push_back(e.b);
  if (solist) {
    for (int i = (!use_a); i < (int)e.elist.size(); i += 2) {
      solist->push_back(e.elist[i].i);
    }
  }
  if (use_a) {
    if (e.even > m) return false;
    if (chk(e.a)) return false;
    pchk[e.a] = true;
    return forceFor(e.a, m, Q, solist);
  } else {
    if (e.odd > m) return false;
    if (chk(e.b)) return false;
    pchk[e.b] = true;
    return forceFor(e.b, m, Q, solist);
  }
}
void dfs2(int u, vector<pair<ELIST*, bool> >& L) {
  for (auto a : xgraph[u]) {
    ELIST& e = evens[a];
    if (!chk_evens[e.eindex]) {
      chk_evens[e.eindex] = true;
      int v = e.a + e.b - u;
      dfs2(v, L);
      L.push_back(make_pair(&e, e.a == u));
    }
  }
}
bool possible(int m, vector<int>* solist = NULL) {
  for (int i = 0; i < n; i++) {
    egraph[i].clear();
    xgraph[i].clear();
    pchk[i] = false;
  }
  for (auto& o : odds) {
    if (o.odd <= m) {
      if (solist) {
        for (int i = 1; i < (int)o.elist.size(); i += 2)
          solist->push_back(o.elist[i].i);
      }
    } else if (o.even <= m) {
      if (chk(o.a) || chk(o.b)) return false;
      pchk[o.a] = true;
      pchk[o.b] = true;
      if (solist) {
        for (int i = 0; i < (int)o.elist.size(); i += 2)
          solist->push_back(o.elist[i].i);
      }
    } else
      return false;
  }
  for (int i = 0; i < (int)evens.size(); i++) {
    ELIST& e = evens[i];
    e.eindex = i;
    egraph[e.a].push_back(i);
    egraph[e.b].push_back(i);
    chk_evens[i] = false;
  }
  vector<int> Q;
  for (int i = 0; i < n; i++) {
    edeg[i] = egraph[i].size();
    if (edeg[i] == 1) {
      Q.push_back(i);
    }
  }
  for (int i = 0; i < (int)Q.size(); i++) {
    int u = Q[i];
    if (edeg[u] == 1) {
      for (int e : egraph[u]) {
        ELIST& ev = evens[e];
        int v = ev.a + ev.b - u;
        if (!chk_evens[e]) {
          int cost1 = ((ev.a == u) ? ev.even : ev.odd);
          if (cost1 <= m && !chk(u)) {
            chk_evens[e] = true;
            pchk[u] = true;
            edeg[u]--;
            edeg[v]--;
            if (edeg[v] == 1) Q.push_back(v);
            if (solist) {
              for (int i = (ev.a != u); i < (int)ev.elist.size(); i += 2) {
                solist->push_back(ev.elist[i].i);
              }
            }
            break;
          } else {
            if (!forceRun(ev, (ev.a == v), m, Q, solist)) return false;
          }
        }
      }
    }
  }
  for (int i = 0; i < (int)evens.size(); i++) {
    ELIST& e = evens[i];
    if (!chk_evens[i]) {
      if (chk(e.a) && chk(e.b)) return false;
      if (chk(e.a)) {
        if (!forceRun(e, false, m, Q, solist)) return false;
      } else if (chk(e.b)) {
        if (!forceRun(e, true, m, Q, solist)) return false;
      }
    }
  }
  for (int i = 0; i < (int)evens.size(); i++) {
    ELIST& e = evens[i];
    if (!chk_evens[i]) {
      xgraph[e.a].push_back(i);
      xgraph[e.b].push_back(i);
    }
  }
  for (int i = 0; i < n; i++) {
    if (xgraph[i].empty()) continue;
    if (xgraph[i].size() == 2) {
      vector<pair<ELIST*, bool> > L;
      dfs2(i, L);
      int all_a, all_b;
      all_a = all_b = 0;
      for (auto& l : L) {
        if (!l.second) {
          all_a = max(l.first->even, all_a);
          all_b = max(l.first->odd, all_b);
        } else {
          all_a = max(l.first->odd, all_a);
          all_b = max(l.first->even, all_b);
        }
      }
      int min_ab = min(all_a, all_b);
      if (min_ab > m) return false;
      bool use_a = (min_ab == all_a);
      if (solist) {
        for (auto& l : L) {
          vector<EDGE>& elist = l.first->elist;
          for (int i = (use_a == l.second); i < (int)elist.size(); i += 2) {
            solist->push_back(elist[i].i);
          }
        }
      }
    } else {
      return false;
    }
  }
}
int main() {
  int m;
  scanf("%d %d", &n, &m);
  int maxt = 0;
  for (int i = 0; i < m; i++) {
    int a, b, c, t;
    scanf("%d %d %d %d", &a, &b, &c, &t);
    maxt = max(maxt, t);
    if (cmap.find(c) == cmap.end()) {
      cmap[c] = ccnt++;
    }
    c = cmap[c];
    a--;
    b--;
    clist[c].push_back(make_pair(a, lst[a].size()));
    clist[c].push_back(make_pair(b, lst[b].size()));
    lst[a].push_back(EDGE(b, c, t, i));
    lst[b].push_back(EDGE(a, c, t, i));
  }
  bool pos = true;
  int sol = 0;
  vector<int> solist;
  for (int i = 0; i < ccnt; i++) {
    map<int, int> deg;
    for (auto p : clist[i]) {
      ll[p.first].push_back(lst[p.first][p.second]);
      deg[p.first] = ll[p.first].size();
    }
    vector<int> deg1, deg2;
    for (auto d : deg) {
      if (d.second > 2) pos = false;
      if (d.second == 1) {
        deg1.push_back(d.first);
      } else if (d.second == 2) {
        deg2.push_back(d.first);
      }
    }
    if (!pos) break;
    vector<int> vlist;
    for (int u : deg1) vlist.push_back(u);
    for (int u : deg2) vlist.push_back(u);
    for (int v : vlist) {
      vector<EDGE> elist;
      dfs(v, elist);
      if (elist.empty()) continue;
      int odd, even;
      odd = even = 0;
      for (int i = 0; i < (int)elist.size(); i++) {
        EDGE& e = elist[i];
        if (i % 2 == 0)
          even = max(even, e.t);
        else
          odd = max(odd, e.t);
      }
      if (deg[v] == 1) {
        for (int i = 0; i + 1 < (int)elist.size(); i++) {
          EDGE& e = elist[i];
          if (vchk[e.who]) pos = false;
          vchk[e.who] = true;
        }
        int va, vb;
        va = v;
        vb = elist[(int)elist.size() - 1].who;
        if (elist.size() % 2 == 1) {
          if (odd <= even) {
            sol = max(sol, odd);
            for (int i = 1; i < (int)elist.size(); i += 2) {
              EDGE& e = elist[i];
              solist.push_back(e.i);
            }
          } else {
            odds.push_back(ELIST(va, vb, odd, even, elist));
          }
        } else {
          evens.push_back(ELIST(va, vb, odd, even, elist));
        }
      } else if (deg[v] == 2) {
        for (int i = 0; i < (int)elist.size(); i++) {
          EDGE& e = elist[i];
          if (vchk[e.who]) pos = false;
          vchk[e.who] = true;
        }
        if (even > odd) {
          sol = max(sol, odd);
          for (int i = 1; i < (int)elist.size(); i += 2) {
            EDGE& e = elist[i];
            solist.push_back(e.i);
          }
        } else {
          sol = max(sol, even);
          for (int i = 0; i < (int)elist.size(); i += 2) {
            EDGE& e = elist[i];
            solist.push_back(e.i);
          }
        }
      }
    }
    if (!pos) break;
    for (auto p : clist[i]) {
      ll[p.first].clear();
    }
  }
  int s = sol, e = maxt;
  while (s <= e) {
    int m = (s + e) / 2;
    if (pos && possible(m)) {
      e = m - 1;
    } else {
      s = m + 1;
    }
  }
  if (e == maxt)
    pos = false;
  else {
    sol = e + 1;
    possible(sol, &solist);
  }
  if (pos) {
    printf("Yes\n");
    printf("%d %d\n", sol, (int)solist.size());
    sort(solist.begin(), solist.end());
    for (int i = 0; i < (int)solist.size(); i++) {
      printf("%d ", solist[i] + 1);
    }
    printf("\n");
  } else {
    printf("No\n");
  }
  return 0;
}
