Magic Potion
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65535/32768 K (Java/Others)
Total Submission(s): 488 Accepted Submission(s): 287
ios
Problem Description
In a distant magic world, there is a powerful magician aswmtjdsj. One day,aswmtjdsj decide to teach his prentice ykwd to make some magic potions. The magic potion is made by 8 kinds of materials, what aswmtjdsj need to do is to tell ykwd how many each kind of materials is required. In order to prevent others from stealing these formulas, he decide to encrypt the formula. Assuming the amount of the eight kinds of materials are x1, x2, ... x8, aswmtjdsj will use a number m to encrypt, and finally tell ykwd nine numbers:x1 xor m, x2 xor m ,...., x8 xor m, (x1 + x2 +...+ x8) xor m . ykwd is too lazy,however,to calculate the value of the number m, so he asks you to help him to find the number m.
Input
The first line is an integer t, the number of test cases.
Each of the next t lines contains 9 integers, respectively, x1 xor m, x2 xor m ,...., x8 xor m, (x1 + x2 +...+ x8) xor m, each of the 9 numbers is less or equal to 2
31-1.
Output
For each test case you should output the value of m in a single line, you can assume that 0 <= m <= 2
31-1.
Sample Input
2 1 2 3 4 5 6 7 8 36 5 5 5 5 5 5 5 5 123
Sample Output
0 11
Hint
The XOR operation takes two bit patterns of equal length and performs the logical XOR operation on each pair of corresponding bits. The result of each digit is 1 if the two bits are different, and 0 if they are the same. For example: 0101 (decimal 5) XOR 0011 (decimal 3) = 0110 (decimal 6)
剛開始接觸這種題時, 一點頭緒都沒有,可是經過本身查資料,寫幾個簡單的案例模擬一下過程,其實仍是很容易理解的。
一會兒沒想出來沒有關係,多試試總會有答案。
主要是弄清楚異或運算 其實和位運算有關係的,將數字轉換爲二進制本身試試,思路會清晰多。
//x << N: 左移N位就至關於原數乘以2的N次方; x >> N : 右移N位 就至關於原數除以2的N次方。
//x 異或 m,設 y = x << m, 即 y 就等於將x 左移(<<) m 位 ,這點很重要!
//設原來的數字爲 xi 與 m 異或後 xi ^m = bi(1 <= i <= 9), (x1+x2+...+x8)^ m = b9 至關於(b1+b2+...+b8) = b9;
//所以 將(b1+b2+...+b8) 每一位與b9的每一位比較,若不相同, 即 意味着原數向左移了 j 位 ,將移動的位數相加即爲 m的值
//很容易想到 若xi沒有移位的話, (b1+b2+...+b8)^m == b9
#include<iostream>
#include<algorithm>
using namespace std;git
int main()
{
int t;
int sum, m, tmp;
cin >> t;
while(t--)
{
int r[10];
for(int i = 1; i <= 9; i++)
{
cin >> r[i];
}
sum = m = 0;
for(int j = 0; j <= 31; j++)
{
tmp = 0;
for(int k = 1; k <= 8; k++)
{
tmp += r[k]>>j&1; //(r[k] / 2^j) & 1, 與m異或後的八個數的和 從右至左 取出它的值,與第九個數的第j位比較
}
if((sum + tmp)%2 != (r[9]>>j&1))//若不一樣,將其轉換爲原數的第i位具備的值, 再求出它的進位值 ,並將m加上 (1左移相應的位數 j )
{
tmp = 8 - tmp;
sum = (sum + tmp) / 2;
m += 1 << j;
}
else
{
sum = (sum + tmp) / 2;//若相同 將進位的用sum加上去,繼續下一位
}
}
cout << m << endl;
}
return 0;
}less