X-man

导航

A. Xor-tree

题目意思:

给一颗n个节点的树,每个节点有一个值要么是0要么是1,改变某个节点的值时,它的儿子不变,它儿子的儿子翻转,它儿子的儿子的儿子不变,如此类推。给定各个节点的目标值,求最少的翻转次数,使得达到要求。

题解思路:

贪心+Dfs

判断当前节点的值,与目标值比较

1.当前节点值由其上上一个节点值是否需要改变决定。

2.Dfs每次传参p1,p2表示上前两层的节点改变。

(通过p1,p2的交换,实现间隔改变节点值,同时实现累加的改变值)

#include<stdio.h>
#include<vector>
using namespace std;
const int MAX = 100100;
vector<int>edge[MAX];
bool init[MAX];
bool goal[MAX];
int num;
int ans[MAX];
void Dfs(int cur,int p1,int p2,int fa)
{
    if(init[cur]^p1!=goal[cur])
    {
        ans[num++]=cur;
        //printf("tmp:%d\n",cur);
        p1=1-p1;
    }
    for(int i=0;i<edge[cur].size();i++)
    {
        if(edge[cur][i]==fa)continue;
        Dfs(edge[cur][i],p2,p1,cur);
    }
}
int main()
{
    int n;
    int i,j;
    int x,y;
    while(scanf("%d",&n)!=EOF)
    {
        for(i=1;i<n;i++)
            edge[i].clear();
        for(i=1;i<n;i++)
        {
            scanf("%d %d",&x,&y);
            edge[x].push_back(y);
            edge[y].push_back(x);
        }
        for(i=1;i<=n;i++)
            scanf("%d",&init[i]);
        for(i=1;i<=n;i++)
            scanf("%d",&goal[i]);
        num=0;
        Dfs(1,0,0,0);
        printf("%d\n",num);
        for(i=0;i<num;i++)
            printf("%d\n",ans[i]);
    }
}

 

posted on 2014-07-05 16:16  雨钝风轻  阅读(630)  评论(0编辑  收藏  举报