本文參考自《劍指offer》一書,代碼採用Java語言。html
更多:《劍指Offer》Java實現合集 java
在一個數組中除了一個數字只出現一次以外,其餘數字都出現了三次。請找出那個只出現一次的數字。數組
這道題中數字出現了三次,沒法像56-1) 數組中只出現一次的兩個數字同樣經過利用異或位運算進行消除相同個數字。可是仍然能夠沿用位運算的思路。post
將全部數字的二進制表示的對應位都加起來,若是某一位能被三整除,那麼只出現一次的數字在該位爲0;反之,爲1。測試
測試算例 url
1.功能測試(惟一出現的數字是0,正數,負數;重複出現的數字是0,正數,負數)htm
//題目:在一個數組中除了一個數字只出現一次以外,其餘數字都出現了三次。請 //找出那個只出現一次的數字。 public class NumberAppearingOnce { public static int findNumberAppearingOnce(int[] arr) { if(arr==null || arr.length<=0) throw new RuntimeException(); int[] bitSum = new int[32]; for(int i=0;i<32;i++) bitSum[i]=0; for(int i=0;i<arr.length;i++) { int bitMask=1; for(int j=31;j>=0;j--) { int bit=arr[i]&bitMask; //注意arr[i]&bitMask不必定等於1或者0,有可能等於00010000 if(bit!=0) bitSum[j]+=1; bitMask=bitMask<<1; } } int result=0; for(int i=0;i<32;i++) { result=result<<1; result+=(bitSum[i]%3); //result=result<<1; //不能放在後面,不然最前面一位就沒了 } return result; } }
1.判斷某個數x的第n位(如第3位)上是否爲1,blog
1)經過 x&00000100 的結果是否爲0 來判斷。(不能根據是否等於1來判斷)get
2)經過(x>>3)&1 是否爲0 來判斷it
2.經過number&bitMask的結果是否爲0(不能用1判斷),bitMask=1不斷左移,能夠將一個數的二進制存儲到32位的數組中。
int number=100; int bitMask=1; for(int j=31;j>=0;j--) { int bit=number&bitMask; //注意arr[i]&bitMask不必定等於1或者0,有可能等於00010000 if(bit!=0) bits[j]=1; bitMask=bitMask<<1; }
3.經過如下代碼實現二進制轉化爲數字(注意左移語句的位置):
int result=0; for(int i=0;i<32;i++) { result=result<<1; result+=bits[i]; //result=result<<1; //不能放在後面,不然最前面一位就沒了 }