#include<iostream>
#include<cstdio>
using namespace std;
#define ll long long
#define ls k<<1
#define rs k<<1|1
const int maxn=1e6;
int n,m,Lc,Rc;
struct node{
int to,next;
}e[maxn<<1];
int h[maxn],cnt,dad[maxn],dep[maxn],fson[maxn],hson[maxn],tp[maxn],id[maxn],num[maxn],z[maxn];
long long read(){
long long ans=0;
char last=' ',ch=getchar();
while(ch<'0' || ch>'9')last=ch,ch=getchar();
while(ch>='0' && ch<='9')ans=ans*10+ch-'0',ch=getchar();
if(last=='-')ans=-ans;
return ans;
}
void add(int u,int v){
e[++cnt].to=v;
e[cnt].next=h[u];
h[u]=cnt;
}
struct meanless{
int l,r,f;
int lc,rc;
int ans;
}t[maxn*4];
void dfs(int k,int from){
dad[k]=from;
dep[k]=dep[from]+1;
fson[k]=1;
int maxx=0;
for(int i=h[k];i;i=e[i].next){
int v=e[i].to;
if(v!=from) {
dfs(v,k);
fson[k]+=fson[v];
if(fson[v]>maxx) {
hson[k]=v;
maxx=fson[v];
}
}
}
}
void dfs1(int u,int top){
tp[u]=top;
id[u]=++cnt;
num[cnt]=z[u];
if(!hson[u]) return ;
dfs1(hson[u],top);
for(int i=h[u];i;i=e[i].next){
int v=e[i].to;
if(!id[v]) dfs1(v,v);
}
}
void pushdown(int k){
if(!t[k].f) return ;
t[ls].f=t[rs].f=t[k].f;
t[ls].ans=t[rs].ans=1;
t[ls].lc=t[ls].rc=t[rs].lc=t[rs].rc=t[k].f;
t[k].f=0;
}
void date(int k){
t[k].ans=t[ls].ans+t[rs].ans;
if(t[ls].rc==t[rs].lc) t[k].ans--;
t[k].lc=t[ls].lc;
t[k].rc=t[rs].rc;
return ;
}
void build(int k,int l,int r){
t[k].l=l;
t[k].r=r;
if(l==r){
t[k].ans=1;
t[k].rc=t[k].lc=num[l];
return ;
}
int mid=l+r>>1;
build(ls,l,mid);
build(rs,mid+1,r);
date(k);
}
void change(int k,int l,int r,int val){
if(t[k].l>=l&&t[k].r<=r) {
t[k].f=val;
t[k].ans=1;
t[k].lc=t[k].rc=val;
return ;
}
pushdown(k);
int mid=t[k].l+t[k].r>>1;
if(mid>=l) change(ls,l,r,val);
if(mid<r) change(rs,l,r,val);
date(k);
}
int qnum(int k,int l,int r,int R,int L){
if(t[k].l==L) Lc=t[k].lc;
if(t[k].r==R) Rc=t[k].rc;
if(t[k].l==l&&t[k].r==r) return t[k].ans;
pushdown(k);
int mid=t[k].l+t[k].r>>1;
if(r<=mid) return qnum(ls,l,r,R,L);
else if(l>mid) return qnum(rs,l,r,R,L);
else {
int ans=qnum(ls,l,r,R,L)+qnum(rs,l,r,R,L);
if(t[ls].rc==t[rs].lc) ans--;
return ans;
}
}
void treenum(int x,int y){
int ans1=-1,ans2=-1;
int temp=0;
while(tp[x]!=tp[y]){
if(dep[tp[x]]<dep[tp[y]]) {swap(x,y);swap(ans1,ans2);}
temp+=qnum(1,id[tp[x]],id[x],id[x],id[tp[x]]);
if(Rc==ans1) temp--;
x=dad[tp[x]];
ans1=Lc;
}
if(dep[x]<dep[y]) {swap(x,y);swap(ans1,ans2);}
temp+=qnum(1,id[y],id[x],id[x],id[y]);
if(Rc==ans1) temp--;
if(Lc==ans2) temp--;
printf("%d\n",temp);
}
void treeadd(int x,int y,int val){
while(tp[x]!=tp[y]){
if(dep[tp[x]]<dep[tp[y]]) swap(x,y);
change(1,id[tp[x]],id[x],val);
x=dad[tp[x]];
}
if(dep[x]<dep[y]) swap(x,y);
change(1,id[y],id[x],val);
}
int main(){
int a,b;cin>>n>>m;
for(int i=1;i<=n;++i)
z[i]=read();
for(int i=1;i<n;++i) {a=read();b=read();add(a,b);add(b,a);}
dfs(1,0);
cnt=0;
dfs1(1,1);
build(1,1,n);
char ai;
ll x,y,z;
while(m--){
cin>>ai;
x=read();y=read();
if(ai=='C') { z=read();treeadd(x,y,z);}
else treenum(x,y);
}
}