#include <cstdio>
#include <cstring>
#include <set>
#include <vector>

const int N = 100000;
const int A = 20;
int n, m, indeg[N], start[N], end[N], to[A][A], ind[N], prev[1 << A][A];
std::vector<int> g[N], g1[N], out[N];
bool ok = 1, vis[N], d[1 << A][A];

std::set<std::pair<int, int> > added;
void add(int u, int v) {
	if (added.insert(std::make_pair(u, v)).second) {
		g1[u].push_back(v);
		++indeg[v];
	}
}

int cur;
int dfssnake(int v) {
	vis[v] = 1;
	start[v] = cur;
	if (g1[v].size() > 1) ok = 0;
	for (int i = 0; i < (int)g1[v].size(); ++i) {
		if (vis[g1[v][i]]) ok = 0;
		return dfssnake(g1[v][i]);
	}
	return v;
}

std::vector<int> ans;
void generate(int v) {
	ans.push_back(v);
	vis[v] = 1;
	for (int i = 0; i < (int)g1[v].size(); ++i) if (!vis[g1[v][i]]) generate(g1[v][i]);
}

bool checkedge(int a, int b) {
	int i;
	for (i = 0; i < (int)g1[a].size() && g1[a][i] != b; ++i);
	if (i == g1[a].size()) return 0;
	return 1;
}

int main() {
	scanf("%d%d", &n, &m);
	for (int i = 0; i < m; ++i) {
		int a, b;
		scanf("%d%d", &a, &b);
		--a;
		--b;
		g[a].push_back(b);
		out[b].push_back(a);
	}
	for (int i = 0; i < n; ++i) {
		if (!g[i].size() || !out[i].size()) {
			printf("NO\n");
			return 0;
		}
		if (g[i].size() == 1) add(i, g[i].back());
		if (out[i].size() == 1) add(out[i].back(), i);
	}
	bool any = 0;
	for (int i = 0; i < n; ++i) if (!indeg[i]) {
		any = 1;
		cur = i;
		end[i] = dfssnake(i);
	}
	if (any) {
		for (int i = 0; i < n; ++i) if (!vis[i]) ok = 0;
		if (!ok) {
			printf("NO\n");
			return 0;
		}
		std::vector<int> all;
		for (int i = 0; i < n; ++i) if (start[i] == i) {
			ind[i] = all.size();
			all.push_back(i);
		}
		int cnt = all.size();
		for (int i = 0; i < n; ++i) if (end[start[i]] = i) for (int j = 0; j < (int)g[i].size(); ++j) if (start[g[i][j]] == g[i][j]) to[ind[start[i]]][ind[g[i][j]]] = 1;
		d[1][0] = 1;
		for (int i = 1; i + 1 < 1 << cnt; ++i) for (int j = 0; j < cnt; ++j) if (d[i][j]) {
			for (int k = 0; k < cnt; ++k) if (i >> k & 1 ^ 1 && to[j][k]) {
				d[i | 1 << k][k] = 1;
				prev[i | 1 << k][k] = j;
			}
		}
		int i;
		for (i = 0; i < cnt; ++i) if (d[(1 << cnt) - 1][i] && to[i][0]) break;
		if (i == cnt) {
			printf("NO\n");
			return 0;
		}
		g1[end[all[i]]].push_back(all[0]);
		int mask = (1 << cnt) - 1;
		while (i) {
			g1[end[all[prev[mask][i]]]].push_back(all[i]);
			int mask1 = mask & ~(1 << i);
			i = prev[mask][i];
			mask = mask1;
		}
		memset(vis, 0, n);
	}
	generate(0);
	if (ans.size() != n || !checkedge(ans.back(), 0)) {
		printf("NO\n");
		return 0;
	}
	printf("YES\n");
	for (int i = 0; i < (int)ans.size(); ++i) printf("%d ", ans[i] + 1);
	printf("1\n");
	return 0;
}