一、前言
- 筆者準備參加藍橋杯,所以再次記錄自己的學習心得。
- 我會將自己的演算法學習之路用部落格進行記錄,並將學習思想進行分享。
- 希望大家如果看文章的話,可以認真閱讀題目,並進行思考。
- 希望和大家一起共同成長
二、奇妙的異或
1-1000這1000個數放在含有1001個元素的陣列中,只有唯一的一個元素值重複,其它均只出現一次。每個陣列元素只能訪問一次,設計一個演算法,將它找出來;不用輔助儲存空間,能否設計一個演算法實現?
前置知識:
- 一個數與本身進行異或,結果為0。A ^ A = 0
- 任何數與零進行異或,結果為本身。 B ^ 0 = B
演算法思想:
- 透過閱讀題目,我們可以利用異或性值,將1——1000這組資料複製一份,與原先的這組數進行異或,那麼我們重複的元素就會出現3次,而其他元素只出現兩次。
- 所以我們可以得出最後的結果
// A ^ A = 0
// B ^ 0 = B
public class 唯一成對的數 {
public static void main(String[] args) {
int N = 101;
int[] arr = new int[N];
for(int i = 0; i < arr.length-1; i++) {
arr[i] = i+1;
}
// 最後一個隨機數
arr[arr.length-1] = new Random().nextInt(N);
// 隨機下標
int index = new Random().nextInt(N);
// 隨機交換
Utils.swap(arr, index, arr.length-1);
System.out.println(Arrays.toString(arr));
int res = 0;
// 讓 res 與 1..100進行異或運算
for(int i = 1; i <= N-1; i++) {
res = res ^ i;
}
// 讓 1..100和多的一位數,與res進行異或,當兩個1..100進行異或時為0,所以答案就是剩下的最後一個值
for(int i = 0; i < N; i++) {
res = res ^ arr[i];
}
System.out.println(res);
}
}
三、奇妙的運算
請實現一個函式,輸入一個整數,輸出該數二進位制表示中1的個數。
例如9的二進位制1001,有2個1
前置知識:
- 與運算 1 & 1 = 1、1 & 0=0
- 移位
演算法思想————解法一:
- 我們可以讓該數與1從右至左進行與運算。這樣如果結果為1,那麼就是1,我們在進行判斷是否相等。
- 每一次都需要將我們的1左移一位,也相當於對該二進位制數進行掃描
public class 二進位制1的個數 {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
int N = sc.nextInt();
System.out.println(Integer.toString(N,2));
int count = 0;
// 讓1移位,與二進位制每一個數進行 與運算
for (int i = 0; i < 32; i++) {
if((N & (1 << i)) == (1 << i)) {
count++;
}
}
System.out.println(count);
}
}
演算法思想————解法二:
- 可以採用該數-1操作,然後與原來的數進行與運算,這樣我們可以消除最右邊的1,直接把1全部消掉,結果為0為止。
// 因為二進位制-1後和 原先的值進行 與運算,會消除最右邊的1
System.out.println("解法二-----------------");
count = 0;
while(N!=0) {
N = (N-1)&N;
count++;
}
System.out.println(count);
四、簡單的程式碼
用一條語句判斷一個整數是不是2的整數次方。
演算法思想:
- 我們知道2的整數次方的二進位制,應該是隻含有一個1的
- 所以本題我們就可以變解為求二進位制中是否存在一個1
- 利用我們上面所學的求1的個數,那麼我們很快就可以解決。
if( ((N-1)&N)) == 0) return true;
五、複雜的運算
陣列中只有一個數出現了1次,其他的數都出現了k次,請輸出只出現了1次的數。
前置知識:
- 2個相同的2進位制數做不進位加法,結果為0
- 10個相同的10進位制數做不進位加法,結果為0
- k個相同的k進位制數做不進位加法,結果為0
演算法思想:
- 所以本題我們可以將出現k次的數,轉換為k進位制,然後進行加法運算。
- 我們還需要將數字進行翻轉,這樣才能夠保證我們在做加法運算時,最低位是對齊的。
- 其實我們可以採用雜湊錶速速解決戰鬥,但是我們學習的是位運算的思想。
六、結尾
- 對於藍橋杯位運算知識內容就總結這麼多,若想深入學習等待後續更新。
- 我將會繼續更新關於藍橋杯方向的學習知識,感興趣的小夥伴可以關注一下。
- 文章寫得比較走心,用了很長時間,絕對不是copy過來的!
- 尊重每一位學習知識的人,同時也尊重每一位分享知識的人。
- ?你的點贊與關注,是我努力前行的無限動力。?