#include <cassert>// c
#include <ctime>
#include <iostream>// io
#include <iomanip>
#include <fstream>
#include <sstream>
#include <vector>// container
#include <map>
#include <set>
#include <queue>
#include <bitset>
#include <stack>
#include <algorithm>// other
#include <complex>
#include <numeric>
#include <functional>
#include <random>
#include <regex>

using namespace std;
typedef long long ll;

#define ALL(c) (c).begin(),(c).end()
#define FOR(i,l,r) for(int i=(int)l;i<(int)r;++i)
#define REP(i,n) FOR(i,0,n)
#define FORr(i,l,r) for(int i=(int)r-1;i>=(int)l;--i)
#define REPr(i,n) FORr(i,0,n)
#define EACH(i,c) for(__typeof((c).begin()) i=(c).begin(); i!=(c).end(); ++i)
#define IN(l,v,r) ((l)<=(v) && (v)<(r))
#define UNIQUE(v) v.erase(unique(ALL(v)),v.end())
//debug
#define DUMP(x)  cerr << #x << " = " << (x)
#define LINE()    cerr<< " (L" << __LINE__ << ")"

template<typename T,typename U> T pmod(T x,U M){return (x%M+M)%M;}

//verified by AOJ0118 
struct UnionFind{
    vector<int> par,rank,ss;int size;
    vector<int> ws;
    UnionFind(int n){
        REP(i,n) par.push_back(i);
        rank = vector<int>(n);ss=vector<int>(n,1);size=n;

        ws=vector<int>(n);
    }
    int root(int x){
        if(par[x] == x)return x;
        int r = root(par[x]); ws[x] += ws[par[x]];
        return par[x] = r;
    }
    int val(int x){
    	root(x);return ws[x];
    }
    bool same(int x,int y){
        return root(x) == root(y);
    }
    void unite(int x,int y,int w=0){
    	int vx=val(x),vy=val(y);
        x = root(x);y = root(y);
        if(x==y)return;
        if(rank[x] < rank[y]){//root y
        	ws[x] = w + vy - vx;
             par[x] = y;ss[y]+=ss[x];
        }else{//root x
        	ws[y] = -w +vx - vy;
            par[y] = x;ss[x]+=ss[y];
        }
        if(rank[x] == rank[y]) rank[x]++;
        size--;
    }
    int getS(int x){
        return ss[root(x)];
    }
};

int main() {
	cin.tie(0);
	ios::sync_with_stdio(false);
	cerr << fixed <<setprecision(20);
	cout << fixed <<setprecision(20);
  while (true) {
  	int N,M;cin >> N >> M;if(N==0)break;
  	UnionFind uf(N);
  	REP(i,M){
  		char c;int a,b,w;cin >> c >> a >> b;a--;b--;
	
		// REP(i,N)cerr <<uf.par[i] <<" ";cerr <<endl;
  // 		REP(i,N)cerr <<uf.val(i) <<" ";cerr <<endl;
  		if(c=='!'){
  			cin >> w;
  			uf.unite(a,b,w);
  		}else{
  			if(!uf.same(a,b)){
  				cout <<"UNKNOWN"<<endl;
  			}else{
  				cout << uf.val(a)-uf.val(b) <<endl;
  			}
  		}
  		// cerr <<"aaa"<<endl;
  	}
  }
}