//#pragma GCC optimize(2)
//#include <bits/stdc++.h>
#include <set>
#include <vector>
#include <iostream>
using namespace std;
typedef long long ll;
#define rep(i, beg, end) for (int i = (beg); i < (end); i++)

struct cmp
{
    bool operator()(pair<int, int> a, pair<int, int> b)
    {
        if (a.first != b.first)
        {
            if (a.second == b.second)
            {
                return a.first < b.first;
            }
            else
            {
                return a.second < b.second;
            }
        }
        else
        {
            return a.second < b.second;
        }
    }
};

int edgeTo[100000 + 5];
int distTo[100000 + 5];
set<pair<int, int>, cmp> pq;
void relax(int from, int to, int weight)
{
    if (distTo[to] > distTo[from] + weight)
    {
        pair<int, int> backup = {to, distTo[to]};
        distTo[to] = distTo[from] + weight;
        edgeTo[to] = from;
        if (pq.find(backup) != pq.end())
        {
            pq.erase(backup);
            pq.insert({to, distTo[to]});
        }
        else
        {
            pq.insert({to, distTo[to]});
        }
    }
}

void dijsktra(vector<vector<pair<int, int>>> g, int s)
{
    int n = g.size();
    for (int i = 0; i < n + 1; i++)
    {
        distTo[i] = 2147483647;
    }

    distTo[s] = 0;
    pq.insert({s, 0});
    while (!pq.empty())
    {
        auto it = pq.begin();
        pair<int, int> top = *it;
        pq.erase(*it);
        for (pair<int, int> e : g[top.first])
        {
            relax(top.first, e.first, e.second);
        }
    }
}

int main()
{
    int n, m;
    cin >> n >> m;
    vector<vector<pair<int, int>>> graph(n + 1);
    rep(i, 1, m + 1)
    {
        int a, b;
        cin >> a >> b;
        graph[a].push_back({b, 1});
        graph[b].push_back({a, 1});
    }
    dijsktra(graph, 1);

    cout << "Yes" << endl;
    rep(i, 2, n + 1)
    {
        cout << edgeTo[i] << endl;
    }
    return 0;
}