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>
using namespace std;
const int inf = 1e9;
const double eps = 1e-9;
const double pi = 4 * atan(1.0);
const int N = int(1e6) + 100;
struct edge {
  int v, u, c, t;
};
int n, m, ptr;
edge e[N];
bool used[N];
int t[N], ord[N], col[N];
vector<pair<int, int> > g[N];
vector<int> dg[N], rg[N];
vector<int> lst;
inline void fail() {
  puts("No");
  exit(0);
}
inline void add(int a, int b) {
  dg[a].push_back(b);
  rg[b].push_back(a);
}
void dfs1(int v) {
  used[v] = true;
  for (int i = 0; i < ((int)(dg[v]).size()); ++i) {
    if (!used[dg[v][i]]) {
      dfs1(dg[v][i]);
    }
  }
  ord[ptr++] = v;
}
void dfs2(int v) {
  col[v] = ptr;
  for (int i = 0; i < ((int)(rg[v]).size()); ++i) {
    if (col[rg[v][i]] == -1) {
      dfs2(rg[v][i]);
    }
  }
}
inline bool check(int t) {
  for (int i = 0; i < 2 * m; ++i) {
    dg[i].clear();
    rg[i].clear();
  }
  int sz = 2 * m;
  for (int i = 0; i < n; ++i) {
    sort((g[i]).begin(), (g[i]).end());
    for (int it = 0; it < 2; ++it) {
      int ver = g[i][0].second * 2;
      for (int j = 1; j < ((int)(g[i]).size()); ++j) {
        add(g[i][j].second * 2 + 1, ver);
        int nver = sz++;
        dg[nver].clear();
        rg[nver].clear();
        add(nver, ver);
        add(nver, g[i][j].second * 2);
        ver = nver;
      }
      reverse((g[i]).begin(), (g[i]).end());
    }
    int j = 0;
    while (j < ((int)(g[i]).size())) {
      int z = j;
      while (z + 1 < ((int)(g[i]).size()) &&
             g[i][j].first == g[i][z + 1].first) {
        ++z;
      }
      if (z - j + 1 > 2) {
        fail();
      }
      if (z - j + 1 == 2) {
        add(g[i][j].second * 2, g[i][j + 1].second * 2 + 1);
        add(g[i][j + 1].second * 2, g[i][j].second * 2 + 1);
      }
      j = z + 1;
    }
  }
  for (int i = 0; i < m; ++i) {
    if (e[i].t > t) {
      add(i * 2 + 1, i * 2);
    }
  }
  for (int i = 0; i < sz; ++i) {
    col[i] = -1;
    used[i] = false;
  }
  ptr = 0;
  for (int i = 0; i < sz; ++i) {
    if (!used[i]) {
      dfs1(i);
    }
  }
  for (int i = sz - 1; i >= 0; --i) {
    if (col[ord[i]] == -1) {
      dfs2(ord[i]);
      ++ptr;
    }
  }
  for (int i = 0; i < m; ++i) {
    if (col[i * 2] == col[i * 2 + 1]) {
      return false;
    }
  }
  return true;
}
int main() {
  cin >> n >> m;
  for (int i = 0; i < m; ++i) {
    scanf("%d %d %d %d", &e[i].v, &e[i].u, &e[i].c, &e[i].t);
    --e[i].v;
    --e[i].u;
    g[e[i].v].push_back(make_pair(e[i].c, i));
    g[e[i].u].push_back(make_pair(e[i].c, i));
    t[i] = e[i].t;
  }
  t[m] = 0;
  sort(t, t + m + 1);
  int k = unique(t, t + m + 1) - t;
  int res = -1, l = 0, r = k - 1;
  while (l <= r) {
    int mid = (l + r) / 2;
    if (check(t[mid])) {
      res = mid;
      r = mid - 1;
    } else {
      l = mid + 1;
    }
  }
  if (res == -1) {
    fail();
  }
  for (int i = 0; i < m; ++i) {
    if (col[i * 2] < col[i * 2 + 1]) {
      lst.push_back(i);
    }
  }
  printf("Yes\n%d %d\n", t[res], ((int)(lst).size()));
  for (int i = 0; i < ((int)(lst).size()); ++i) {
    printf("%d ", lst[i] + 1);
  }
  puts("");
  return 0;
}
