二進制1的個數

題目描述

輸入一個整數,輸出該數二進制表示中1的個數。其中負數用補碼錶示。

可能引起死循環的解法

class Solution {
public:
  int  NumberOf1(int n) {
    int cnt = 0;
    while (n) {
      if (n & 1) cnt++;
      n >>= 1;
    }
    return cnt;
  }
};

由於數字在計算機中的二進制存儲事實上並不包含符號(也就是±),都是統一用補碼錶示的。
移位操作會保證數的正負不變,當遇到一個負數,右移到最前面的符號位1時,再往右移並不會變成期待的0,最高位永遠保持爲1,這就會死循環。

改進(非通用)

我們假定這裏的整數就是佔32位,那麼就可以固定住枚舉次數,但是不一定通用(實際上我們是假設這個整數就是32位二進制存儲的)

class Solution {
public:
  int  NumberOf1(int n) {
    int cnt = 0;
    for (int i = 0; i < 32; i++) {
      if (n >> i & 1) cnt++;
    }
    return cnt;
  }
};

一般解法:

class Solution {
public:
  int  NumberOf1(int n) {
    int cnt = 0;
    unsigned flag = 1;
    while (flag) {
      if (n & flag) cnt++;
      flag <<= 1;
    }
    return cnt;
  }
};

最優解法

這個方法的好處在於,有多少個1就只需要循環多少次

class Solution {
public:
  int  NumberOf1(int n) {
    int cnt = 0;
    while (n) {
      cnt++;
      n = n & (n - 1); // n & (n - 1)的作用相當於將這個數的最後一個1變成0
    }
    return cnt;
  }
};
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章