#include <bits/stdc++.h>
using namespace std;
using ll = long long;
template<class T> using vec = vector<T>;
template<class T> using vvec = vector<vec<T>>;

struct edge{
    int to,id;
    ll dist;
    edge(int to,ll dist=1,int id=1):to(to),id(id),dist(dist){};
};

class LCA{
private:
    int N;
	vvec<edge> v;
	vvec<int> parent;
	vec<int> depth,ord,ov;
    vec<ll> dist;
    int h = 0;
    int k;
	void dfs(int cur,int par,int d){
		parent[0][cur] = par;
		depth[cur] = d;
        ov[k] = cur;
        ord[cur] = k++;
		for(auto& e:v[cur]) if(e.to!=par){
            dist[e.to] = dist[cur]+e.dist;
			dfs(e.to,cur,d+1);
		}
	}
public:
	LCA(int N,int root,vvec<edge>& tree):N(N){
		while((1<<h)<=N) h++;
        v = tree;
		parent = vvec<int>(h,vec<int>(N,0));
		depth = ord = ov = vec<int>(N,0);
        dist = vec<ll>(N,0);
		k = 0;
        dfs(root,-1,0);
		for(int j=0;j+1<h;j++){
			for(int i=0;i<N;i++){
				if(parent[j][i]<0) parent[j+1][i] = -1;
				else parent[j+1][i] = parent[j][parent[j][i]];
			}
		}
	}
	int lca(int n,int m){
		if(depth[n]>depth[m]) swap(n,m);
		for(int j=0;j<h;j++){
			if((depth[m]-depth[n]) >> j&1) m = parent[j][m];
		}
		if(n==m) return n;
		for(int j=h-1;j>=0;j--){
			if(parent[j][n]!=parent[j][m]){
				n = parent[j][n];
				m = parent[j][m];
			}
		}
		return parent[0][n];
	}
    int dep(int n){return depth[n];}
    ll getdist(int n){return dist[n];}
    int getord(int n){return ord[n];}
    int getordist(int o){return dist[ov[o]];}
    int getov(int o){return ov[o];}
};

int main(){
    int N;
    cin >> N;
    vvec<edge> g(N);
    for(int i=0;i<N-1;i++){
        int a,b;
        cin >> a >> b;
        a--; b--;
        g[a].push_back(b);
        g[b].push_back(a);
    }
    LCA lca(N,0,g);
    const int C = 100000;
    vec<set<int>> colset(C,set<int>());
    vec<int> colv(N);
    vec<int> res(C,-2);
    for(int i=0;i<N;i++){
        int c;
        cin >> c;
        c--;
        colset[c].insert(lca.getord(i));
        colv[i] = c;
    }

    auto calc = [&](int a,int b){
        return lca.getordist(a)+lca.getordist(b)-2*lca.getdist(lca.lca(lca.getov(a),lca.getov(b)));
    };

    for(int i=0;i<C;i++){
        if(colset[i].empty()) continue;
        if(colset[i].size()==1){
            res[i] = 0;
            continue;
        }
        res[i] = 0;
        int pre = *colset[i].begin(),s = pre;
        set<int>::iterator it = colset[i].begin();
        it++;
        while(it!=colset[i].end()){
            int now = *it;
            res[i] += calc(pre,now);
            pre = now;
            it++;
        }
        res[i] += calc(pre,s);
    }
    int Q;
    cin >> Q;

    auto add = [&](int v,int col){
        int o = lca.getord(v);
        if(colset[col].empty()){
            colset[col].insert(o);
            res[col] = 0;
            return ;
        }
        set<int>::iterator it = colset[col].upper_bound(o);
        int ne,pre;
        ne = (it!=colset[col].end()? *it:*colset[col].begin());
        pre = (it!=colset[col].begin()? *(--it):*colset[col].rbegin());
        res[col] += calc(pre,o)+calc(o,ne)-calc(pre,ne);
        colset[col].insert(o);
    };

    auto del = [&](int v,int col){
        int o = lca.getord(v);
        set<int>::iterator it = colset[col].upper_bound(o);
        int ne,pre;
        ne = (it!=colset[col].end()? *it:*colset[col].begin());
        it--;
        pre = (it!=colset[col].begin()? *(--it):*colset[col].rbegin());
        res[col] -= calc(pre,o)+calc(o,ne)-calc(pre,ne);
        colset[col].erase(o);
        if(colset[col].empty()) res[col] = -2;
    };

    for(int _=0;_<Q;_++){
        char q;
        cin >> q;
        if(q=='Q'){
            int col;
            cin >> col;
            col--;
            cout << res[col]/2 << endl;
        }else{
            int a,col;
            cin >> a >> col;
            a--; col--;
            del(a,colv[a]);
            add(a,col);
            colv[a] = col;
        }
    }
}


Measured memory_bytes: 39760