HDU 5416

                                        CRB and Tree

                                      Time Limit: 8000/4000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)

Problem Description
CRB has a tree, whose vertices are labeled by 1, 2, …, N. They are connected by N – 1 edges. Each edge has a weight.
For any two vertices u and v(possibly equal), f(u,v) is xor(exclusive-or) sum of weights of all edges on the path from u to v.
CRB’s task is for given s, to calculate the number of unordered pairs (u,v) such that f(u,v) = s. Can you help him?
 

 

Input
There are multiple test cases. The first line of input contains an integer T, indicating the number of test cases. For each test case:
The first line contains an integer N denoting the number of vertices.
Each of the next N - 1 lines contains three space separated integers ab and c denoting an edge between a and b, whose weight is c.
The next line contains an integer Q denoting the number of queries.
Each of the next Q lines contains a single integer s.
1 ≤ T ≤ 25
1 ≤ N ≤ 105
1 ≤ Q ≤ 10
1 ≤ ab ≤ N
0 ≤ cs ≤ 105
It is guaranteed that given edges form a tree.

 

 

Output
For each query, output one line containing the answer.
 

 

Sample Input
1 3 1 2 1 2 3 2 3 2 3 4
 

 

Sample Output
1 1 0
Hint
For the first query, (2, 3) is the only pair that f(u, v) = 2. For the second query, (1, 3) is the only one. For the third query, there are no pair (u, v) such that f(u, v) = 4.
 

 

Author
KUT(DPRK)
 

 

Source
 
题意:给你一棵树,路径上有权值,q个询问每次给你一个A,要你找出所有路径权值异或和为A的方案数
题解:定义一个根节点1,dfs出所有节点与根节点的异或和,   根据异或:a^b=c,那么b^c=a
///1085422276
#include<iostream>
#include<cstdio>
#include<cstring>
#include<string>
#include<algorithm>
#include<queue>
#include<cmath>
#include<map>
#include<bitset>
#include<set>
#include<vector>
using namespace std ;
typedef long long ll;
#define push_back pb
#define mem(a) memset(a,0,sizeof(a))
#define TS printf("111111\n");
#define FOR(i,a,b) for( int i=a;i<=b;i++)
#define FORJ(i,a,b) for(int i=a;i>=b;i--)
#define READ(a) scanf("%d",&a)
#define mod 1000000007
#define inf 100000
#define maxn 300000
inline ll read()
{
    ll x=0,f=1;
    char ch=getchar();
    while(ch<'0'||ch>'9')
    {
        if(ch=='-')f=-1;
        ch=getchar();
    }
    while(ch>='0'&&ch<='9')
    {
        x=x*10+ch-'0';
        ch=getchar();
    }
    return x*f;
}
//******************************************************************
struct ss
{
    int to,next,v;
}e[500001];
int vis[200005],head[200005],t,n;
ll hashs[500005];
void add(int u,int v,int w)
{
    ss kk={v,head[u],w};
    e[t]=kk;
    head[u]=t++;
}
void dfs(int x,int pre)
{
    hashs[pre]++;
    vis[x]=1;
    for(int i=head[x];i;i=e[i].next)
    {//TS;
        if(vis[e[i].to])continue;
        dfs(e[i].to,pre^e[i].v);
    }
}
int main()
{
  int a,b,c;
    int T=read();
    while(T--)
    {
        t=1;mem(head);mem(hashs);mem(vis);
        n=read();
        FOR(i,1,n-1)
        {
            scanf("%d%d%d",&a,&b,&c);
            add(a,b,c);
            add(b,a,c);
        }
        //cout<<t<<endl;
        dfs(1,0);
       /// FOR(i,0,3)cout<<hashs[i]<<" ";
        int q=read();
        FOR(i,1,q)
        {  ll ans=0;
           a=read();
           
            for(int j=0;j<=maxn;j++)
            {if(!hashs[j])continue;
                    if((a^j)==j)ans+=(hashs[j]*(hashs[j]-1));
                    else {
                        ans+=(hashs[j]*hashs[a^j]);
                    }
                    //if(ans!=0)cout<<j<<" "<<ans<<endl;
            }ans=ans/2;
            if(a==0)ans+=n;
            cout<<ans<<endl;
        }

    }
    return 0;
}
代码

 

   特别考虑A==0的情况,最后方案数/2
 
posted @ 2015-09-04 16:50  meekyan  阅读(186)  评论(0编辑  收藏  举报