題目鏈接:

http://acm.hdu.edu.cn/showproblem.php?pid=1850

用到的知識:

(三)尼姆博奕(Nimm Game):有三堆各若干個物品,兩個人輪流從某一堆取任意多的
物品,規定每次至少取一個,多者不限,最后取光者得勝。

    這種情況最有意思,它與二進制有密切關系,我們用(a,b,c)表示某種局勢,首先(0,0,0)顯然是奇異局勢,無論誰面對奇異局勢,都必然失敗。第二種奇異局勢是(0,n,n),只要與對手拿走一樣多的物品,最后都將導致(0,0,0)。仔細分析一下,(1,2,3)也是奇異局勢,無論對手如何拿,接下來都可以變為(0,n,n)的情形。

    計算機算法里面有一種叫做按位模2加,也叫做異或的運算,我們用符號(+)表示這種運算。這種運算和一般加法不同的一點是1+1=0。先看(1,2,3)的按位模2加的結果:

1 =二進制01
2 =二進制10
3 =二進制11 (+)
———————
0 =二進制00 (注意不進位)

    對于奇異局勢(0,n,n)也一樣,結果也是0。

    任何奇異局勢(a,b,c)都有a(+)b(+)c =0。

如果我們面對的是一個非奇異局勢(a,b,c),要如何變為奇異局勢呢?假設 a < b< c,我們只要將 c 變為 a(+)b,即可,因為有如下的運算結果: a(+)b(+)(a(+)b)=(a(+)a)(+)(b(+)b)=0(+)0=0。要將c 變為a(+)b,只要從 c中減去 c-(a(+)b)即可。

    例1。(14,21,39),14(+)21=27,39-27=12,所以從39中拿走12個物體即可達到奇異局勢(14,21,27)。

    例2。(55,81,121),55(+)81=102,121-102=19,所以從121中拿走19個物品
就形成了奇異局勢(55,81,102)。

    例3。(29,45,58),29(+)45=48,58-48=10,從58中拿走10個,變為(29,4
5,48)。

 

 

 

代碼:

 

#include<stdio.h>
int a[110];
int main()
{
int n;
int sum;
while(scanf("%d",&n),n)
{
sum=0;
int ans=0;
for(int i=0;i<n;i++)
{
scanf("%d",&a[i]);
sum^=a[i];
}
for(int i=0;i<n;i++)
{
if(a[i]>(sum^a[i]))ans++;
}
printf("%d\n",ans);
}
return 0;
}



文章來源:http://www.cnblogs.com/kuangbin/archive/2011/11/24/2262389.html