import java.io.*;
import java.util.*;
public class Main {
static StreamTokenizer st = new StreamTokenizer(new BufferedReader(new InputStreamReader(System.in)));
static PrintWriter out = new PrintWriter(new BufferedWriter(new OutputStreamWriter(System.out)));
static int in() throws IOException {
st.nextToken();
return (int) st.nval;
}
static class Edge {
public int to, next, weight;
}
static class Node {
public int num, dis;
public Node(int num, int dis) {
this.num = num;
this.dis = dis;
}
}
static Edge[] edges;
static int[] dis, head, ans;
static boolean[] visited;
static boolean[][] re;
static int n, m, u, v, weight, count = 0;
public static void main(String[] args) throws IOException {
n = in();
m = in();
edges = new Edge[2*m + 1];
head = new int[n + 1];
dis = new int[n + 1];
ans = new int[n + 1];
visited = new boolean[n + 1];
re = new boolean[n + 1][n + 1];
init();
for (int i = 0; i < m; i++) {
u = in();
v = in();
weight = in();
if (re[u][v]) {
for (int j = head[u]; j != -1; j = edges[j].next) {
if (edges[j].next == v) {
edges[j].weight = Math.min(edges[j].weight, weight);
break;
}
}
} else {
addTo(u, v, weight);
re[u][v] = true;
}
}
dijkstra(1);
if (ans[n] == 0) {
out.println("No answer");
} else {
out.print(dis[n] + " " + ans[n]);
}
out.close();
}
public static void dijkstra(int start) {
Queue<Node> heap = new PriorityQueue<>(((o1, o2) -> o1.dis - o2.dis));
heap.offer(new Node(start, 0));
dis[start] = 0;
ans[start] = 1;
while (!heap.isEmpty()) {
Node cur = heap.poll();
int num = cur.num;
if (visited[num]) {
continue;
}
visited[num] = true;
for (int i = head[num]; i != -1; i = edges[i].next) {
int next_v = edges[i].to;
int toV_weight = edges[i].weight;
if (dis[num] + toV_weight < dis[next_v]) {
dis[next_v] = dis[num] + toV_weight;
ans[next_v] = ans[num];
if (!visited[next_v]) {
heap.offer(new Node(next_v, dis[next_v]));
}
} else if (dis[num] + toV_weight == dis[next_v]) {
ans[next_v] += ans[num];
}
}
}
}
public static void addTo(int u, int v, int weight) {
edges[count] = new Edge();
edges[count].to = v;
edges[count].weight = weight;
edges[count].next = head[u];
head[u] = count++;
}
public static void init() {
for (int i = 0; i <= n; i++) {
head[i] = -1;
}
for (int i = 0; i <= n; i++) {
dis[i] = Integer.MAX_VALUE;
}
}
}