The trafic on the Internet is increasing these days due to smartphones. The wireless carriers have to enhance their network infrastructure.

The network of a wireless carrier consists of a number of base stations and lines. Each line connects two base stations bi-directionally. The bandwidth of a line increases every year and is given by a polynomial f(x) of the year x.

Your task is, given the network structure, to write a program to calculate the maximal bandwidth between the 1-st and N-th base stations as a polynomial of x.



Input

The input consists of multiple datasets. Each dataset has the following format:

N M
u1 v1 p1
...
uM vM pM


The first line of each dataset contains two integers N (2 ≤ N ≤ 50) and M (0 ≤ M ≤ 500), which indicates the number of base stations and lines respectively. The following M lines describe the network structure. The i-th of them corresponds to the i-th network line and contains two integers ui and vi and a polynomial pi. ui and vi indicate the indices of base stations (1 ≤ ui, vi ≤ N); pi indicates the network bandwidth.

Each polynomial has the form of:

aLxL + aL-1xL-1 + ... + a2x2 + a1x + a0

where L (0 ≤ L ≤ 50) is the degree and ai's (0 ≤ i ≤ L, 0 ≤ ai ≤ 100) are the coefficients. In the input,

* each term aixi (for i ≥ 2) is represented as <ai>x^<i>
* the linear term (a1x) is represented as <a1>x;
* the constant (a0) is represented just by digits;
* these terms are given in the strictly decreasing order of the degrees and connected by a plus sign ("+");
* just like the standard notations, the <ai> is omitted if ai = 1 for non-constant terms;
* similarly, the entire term is omitted if ai = 0 for any terms; and
* the polynomial representations contain no space or characters other than digits, "x", "^", and "+".



For example, 2x2 + 3x + 5 is represented as 2x^2+3x+5; 2x3 + x is represented as 2x^3+x, not 2x^3+0x^2+1x+0 or the like. No polynomial is a constant zero, i.e. the one with all the coefficients being zero.

The end of input is indicated by a line with two zeros. This line is not part of any dataset.

Output

For each dataset, print the maximal bandwidth as a polynomial of x. The polynomial should be represented in the same way as the input format except that a constant zero is possible and should be represented by "0" (without quotes).

Example

Input

3 3
1 2 x+2
2 3 2x+1
3 1 x+1
2 0
3 2
1 2 x
2 3 2
4 3
1 2 x^3+2x^2+3x+4
2 3 x^2+2x+3
3 4 x+2
0 0


Output

2x+3
0
2
x+2
#include<bits/stdc++.h>
#define rep(i,n)for(int i=0;i<(n);i++)
using namespace std;

vector<int>calc(string s) {
	s += "+";
	vector<int>res(51);
	string t;
	for (char c : s) {
		if (c == '+') {
			if (t.back() == 'x')t += "^1";
			if (t.front() == 'x')t = "1" + t;
			if (count(t.begin(), t.end(), 'x') == 0)res[50] = stoi(t);
			int a = 0, b = 0;
			bool flag = true;
			for (char c : t) {
				if (c == 'x')flag = false;
				else if (c == '^')continue;
				else if (flag)a = a * 10 + c - '0';
				else b = b * 10 + c - '0';
			}
			res[50 - b] = a;
			t = "";
		}
		else t += c;
	}
	return res;
}
void add(vector<int>&a, vector<int>b) {
	rep(i, a.size())a[i] += b[i];
}
void sub(vector<int>&a, vector<int>b) {
	rep(i, a.size())a[i] -= b[i];
}
struct edge { int to; vector<int>cap; int rev; };
bool used[50];
vector<edge>E[50];

void add_edge(int from, int to, vector<int>cap) {
	E[from].push_back({ to,cap,(int)E[to].size() });
	E[to].push_back({ from,cap,(int)E[from].size() - 1 });
}
vector<int>dfs(int v, int t, vector<int>f) {
	used[v] = true;
	if (v == t)return f;
	for (edge&e : E[v]) {
		if (used[e.to] || e.cap == vector<int>(51))continue;
		vector<int>d = dfs(e.to, t, min(f, e.cap));
		if (d != vector<int>(51)) {
			sub(e.cap, d); add(E[e.to][e.rev].cap, d);
			return d;
		}
	}
	return vector<int>(51);
}
int main() {
	int n, m;
	while (scanf("%d%d", &n, &m), n) {
		rep(i, n)E[i].clear();
		rep(i, m) {
			int a, b; string s; cin >> a >> b >> s; a--; b--;
			add_edge(a, b, calc(s));
		}
		vector<int>INF(51, INT_MAX);
		vector<int>res(51);
		while (1) {
			memset(used, 0, sizeof(used));
			vector<int>f = dfs(0, n - 1, INF);
			if (f == vector<int>(51))break;
			add(res, f);
		}
		bool flag = false;
		rep(i, 51) {
			if (res[i] == 0)continue;
			if (flag)printf("+");
			if (i == 50)printf("%d", res[i]);
			else if (i == 49) {
				if (res[i] == 1)printf("x");
				else printf("%dx", res[i]);
			}
			else if (res[i] == 1)printf("x^%d", 50 - i);
			else printf("%dx^%d", res[i], 50 - i);
			flag = true;
		}
		if (!flag)printf("0");
		puts("");
	}
}