#include<iostream>
#include<cstdio>
#include<cstring>
#include<queue>
#include<vector>
#include<cmath>
using namespace std;
const int N = 200005;
struct Node{
int to, weight;
};
int n, m;
int point[2005][2005];
int dis[N];
int d[N];//路径总数
vector<Node> G[N];
bool vis[N];
void dij(){
queue<int> q;
memset(dis, 0xff, sizeof(dis));
d[1] = 1;
vis[1] = 1;
dis[1] = 0;
q.push(1);
while(!q.empty()){
int p = q.front();
q.pop();
for(int i = 0; i < G[p].size(); i++){
int p2 = G[p][i].to;
if(dis[p2] == -1){
dis[p2] = dis[p]+G[p][i].weight;
d[p2] = d[p];//记录路径
if(!vis[p2])
vis[p2] = 1, q.push(p2);
}
else if(dis[p2] == dis[p] + G[p][i].weight)
d[p2] = d[p2] + d[p];
}
}
return ;
}
int main(){
scanf("%d%d", &n, &m);
for(int i = 1; i <= m; i++){
int u, v, c;
scanf("%d%d%d", &u, &v, &c);
if(!point[u][v]){
point[u][v] = 1;
G[u].push_back({v, c});
}
else{
for(int j = 0; j < G[u].size(); j++)//去重
if(G[u][j].to == v){
G[u][j].weight = min(G[u][j].weight, c);
break;
}
}
// G[v].push_back({u, c});
}
dij();
if(dis[n] == -1)
printf("No answer");
else printf("%d %d", dis[n], d[n]);
return 0;
}