/*C: cltt的幸运数
Time Limit: 1 s Memory Limit: 128 MB
Submit
Problem Description
一棵树有n个节点,共m次查询,查询a,b的最近公共祖先是否为好数?若好数的数目是幸运数,输出YES,否则输出NO。
好数:可以表示为2的指数幂。如:1, 2,4,8,16,32,……
幸运数就是素数。
Input
nn(nn表示节点数目,接下来n−1n−1行,每行两个整数 x,yx,y 其中xx是yy的父节点)
mm(表示查询数目,接下来mm行,每行两个整数a,ba,b)
(1≤n≤105,1≤m≤10)(1≤n≤105,1≤m≤10)
Output
YESYES or NONO
Sample Input
12
1 2
1 3
2 5
3 4
3 6
4 7
7 9
7 10
6 8
8 11
8 12
4
9 8
4 7
11 12
10 7
Sample Output
YES*/
#include<iostream>
#include<string.h>
#include<algorithm>
using namespace std;
struct node
{
int fa;
bool vis;
}p[100001];
bool check(int x)
{
if(x==0||x==1)return 0;
if(x==2)return 1;
for(int i=2;i*i<=x;i++)
if(x%i==0)
return 0;
return 1;
}
int lca(int x,int y)
{
p[x].vis=1;
while(x!=p[x].fa)//往上遍历到0
{
p[x].vis=1;
x=p[x].fa;
}//printf("%d\n",x);
while(y!=p[y].fa)//无公共祖先时y=0;
{
if(p[y].vis)
break;
y=p[y].fa;
}//printf("%d\n", y);
return y;
}
int main()
{
int n;
scanf("%d",&n);
for(int i=1;i<=n;i++)
p[i].fa=0;
for(int i=1;i<n;i++)
{
int x,y;
scanf("%d%d",&x,&y);
p[y].fa=x;
}
int o;
int cnt=0;
scanf("%d",&o);
for(int i=0;i<o;i++)
{
int x,y;
scanf("%d%d",&x,&y);
for(int i=0;i<=100001;i++)
p[i].vis=0;
int ans=lca(x,y);
if(!(ans&(ans-1)))//0是本题特例,一般情况写if(ans!=0&&!(ans&ans-1))
cnt++;//printf("%d\n",cnt );
}
if(check(cnt))
printf("YES\n");
else
printf("NO\n");
return 0;
}