#include<algorithm>
#include<cstring>
#include<queue>
#include<cstdio>
using namespace std;
const int maxn = 50000 + 5;
int n,m;
struct Edge{
int v,w;
};
vector<Edge> g[maxn];//邻接矩阵存图
int dis[maxn];//存储距离
bool vis[maxn];
struct State{
int u,d;//点的编号和dis
bool operator<(const State &s) const{
return d < s.d;
}
};
void dijkstra(int s)
{
priority_queue<State> q;
memset(dis,0x3f,sizeof(dis));
q.push(State{1,0}),dis[s] = 0;
while(!q.empty())
{
int u = q.top().u,d = q.top().d;
q.pop();
if(d < dis[u]) continue;
for(int i = 0;i < g[u].size();i++)
{
int v = g[u][i].v,w = g[u][i].w;
if(dis[u] + w < dis[v])
{
dis[v] = dis[u] + w;
q.push(State{v,dis[v]});
}
}
}
}
int main()
{
scanf("%d %d",&n,&m);
while(m--)
{
int u,v;
cin >> u >> v;
g[u].push_back(Edge{v,1});
g[v].push_back(Edge{u,1});
}
dijkstra(1);
int maxn = 0;
for(int i = 1;i <= n;i++)
{
if(dis[i] > maxn)
maxn = dis[i];
}
int x = 0;
int cnt = 0;
for(int i = 1;i <= n;i++)
{
if(dis[i] == maxn)
{
cnt++;
if(x == 0)
x = i;
}
}
printf("%d %d %d",x,maxn,cnt);
return 0;
}