#include <bits/stdc++.h>
using namespace std;
const long long INF = 1LL << 60;
const int SIZE = 1001;
int a[SIZE], b[SIZE];
vector<int> edge[SIZE];
vector<int> cedge[SIZE];
int N, M;
int directed[SIZE];
int bridges = 0;
int bridgesP[SIZE];
bool searched[SIZE];
bool beused[SIZE];
bool isDAG() {
  queue<int> qu;
  for (int i = (1); i < (N + 1); i++) {
    if (cedge[i].size() == 0) qu.push(i);
  }
  int times = 0;
  while (!qu.empty()) {
    int now = qu.front();
    qu.pop();
    times++;
    for (int i = (0); i < (edge[now].size()); i++) {
      int next = edge[now][i];
      directed[next]++;
      if (directed[next] == cedge[next].size()) qu.push(next);
    }
  }
  return times == N;
}
int bridge(int now, int from) {
  if (searched[now]) {
    bridgesP[now]++;
    return beused[now];
  }
  searched[now] = true;
  beused[now] = true;
  int inbrids = 0;
  for (int i = (0); i < (cedge[now].size()); i++) {
    int next = cedge[now][i];
    if (next != from) inbrids += bridge(next, now);
  }
  beused[now] = false;
  if (inbrids - bridgesP[now] <= 0) bridges++;
  return inbrids - bridgesP[now];
}
bool solve(int x) {
  for (int i = (1); i < (N + 1); i++) {
    edge[i].clear();
    cedge[i].clear();
    directed[i] = 0;
    searched[i] = false;
    bridgesP[i] = 0;
  }
  bridges = 0;
  for (int i = (0); i < (M); i++) {
    if (x != i) {
      edge[a[i]].push_back(b[i]);
      cedge[b[i]].push_back(a[i]);
    }
  }
  if (!isDAG()) return false;
  for (int i = (0); i < (M); i++) {
    if (x != i) {
      cedge[a[i]].push_back(b[i]);
    }
  }
  bridge(1, -1);
  if (bridges >= 2) return true;
  return false;
}
int main() {
  cin >> N >> M;
  for (int i = (0); i < (M); i++) {
    cin >> a[i] >> b[i];
  }
  for (int i = (0); i < (M); i++) {
    if (solve(i)) {
      cout << "YES" << endl;
      return 0;
    }
  }
  cout << "NO" << endl;
  return 0;
}
