Do You Like XOR?
Time Limit: 1 Sec Memory Limit: 128 Mb
题目链接http://acm.csu.edu.cn:20080/csuoj/problemset/problem?pid=2324
Description
Do you like XOR? Whatever your answer is, Backlight like XOR very much. Thus, he uses a XOR problem as an encryption algorithm, and apply it to his personal computer. The algorithm is as follow:
1.choose 3 integers a,b,c and a,b (1 <= a < b<= 1018),c (1 <= c <= 1018) .
2.calculate password for
pi = i ⊕ i ⊕ i⋯i(a total of c times)
here, ⊕ means XOR(exclusive OR).
One day, Backlight forget his password. But he remember the 3 integers he use to encrypt. Given the 3 integers, could you help him to calculate out his password?
Input
Input contains multiple test cases. Each test case consists of a pair of integers a, b and c , separated by a space, one pair of integers per line.
Output
For each test case, print a single integer on its own line denoting the password.
Sample Input
1 2 3
6 66 666
Sample Output
3
0
Hint
1⊕1⊕1=1,2⊕2⊕2=2,1⊕2=3
题目大意:给你一个区间[a,b]求a到b的每个数的c次异或的异或值。比如第一个样例:
1异或三次⊕2异或三次。。。
emmm,看起来有点恐怖,毕竟数据有1018。。。但想想异或的性质。。。c为偶数的情况就直接过了。。。(全都是0。。。)c为计数的时候他一定可以拆成偶数+1,所以奇数的时候就是它本身。
那么也就是说我们只要求解a⊕(a+1)⊕(a+2)……⊕b就行了。。。但似乎也不是那么好求。。。
这里就用到前缀的思想了。。。关于a⊕(a+1)⊕(a+2)……⊕b的答案我们只要求f[1,a-1]和f[1,b]就行了,而f[a,b]=f[1,a-1]^ f[1,b]。但这数据颇大,所以我们要找一下规律,(一般而言异或的运算都很有规律。。。):
int sum=0;
for (int i=a; i<=b; i++) sum^=i;
printf ("%d ",sum);
直接写个小程序打表就会发现一个规律:
//求1-a的异或值
if (a%4==1) return 1;
if (a%4==2) return a+1;
if (a%4==3 || a==0) return 0;
return a;
emmm,所以问题就解决了。。。
以下是AC代码:
#include <bits/stdc++.h>
using namespace std;
#define ll long long
ll getans(ll a)
{
if (a%4==1) return 1;
if (a%4==2) return a+1;
if (a%4==3 || a==0) return 0;
return a;
}
int main()
{
ll a,b,c;
while (~scanf ("%lld%lld%lld",&a,&b,&c)){
if (c%2==0) printf ("0\n");
else {
ll a1=getans(a-1);
ll a2=getans(b);
ll ans=a1^a2;
printf ("%lld\n",ans);
}
}
return 0;
}