编程之美1——一个数的二进制表示中1的个数

这里要介绍3种解法

第一种;(常规解法)

数在计算机内部都是用二进制表示的,所以可连续用数n除2

代码1:

<span style="font-size:14px;">#include <iostream>
using namespace std;
int main(void)
{
    int n,m;
    m=0;
    cin>>n;
    while(n)
    {
        if(n%2)    //如果n不能整除2,说明当前n的末尾数为1
            m++;
        n>>=1;    //n右移1位,即n/2
    }
    cout<< m <<endl;
    return 0;
}</span>

第二种:使用位操作

&:若a为1,且b为1,则a&b为1,否则,a&b为0

这里初始化i=0x1;

n&i若为1,则n的末尾为1,否则为0

代码2:

<span style="font-size:14px;">#include <iostream>
using namespace std;
int main(void)
{
   //    使用位操作,1 和 二进制的最后一位进行 与(&) 运算
    int n,i,m;
    m=0;
    i=0x1;
    cin>>n;
    while(n)
    {
        m+=(n&i);
        n>>=1;
    }
    cout << m <<endl;
    return 0;
}</span>

第三种:使用另一种位操作

若n的二进制表示为0010 0000,则第二种算法明显有待改进

可让n与n-1进行 & 运算,若n&(n-1)==0,则为上述情况(n的二进制表示中,只有一位是 0)。

代码3:

<span style="font-size:14px;">#include <iostream>
using namespace std;
int main(void)
{
    int n,m;
    m=0;
    cin>>n;
    while(n)
    {
        n&=(n-1);
        m++;
    }
    cout << m <<endl;

    return 0;
}</span>
时间: 2024-12-17 03:00:08

编程之美1——一个数的二进制表示中1的个数的相关文章

位运算--统计一个数的二进制序列中1的个数

给出一个十进制数,求出该数的二进制序列中1的个数.比如 15 的二进制序列是 00000000  00000000  00000000 00001111   1的个数是4. 下边将给出几种不同的解决办法: 方法一: int count_one(int num) { int count = 0; while (num) { if (num % 2 == 1) { count++; } num = num / 2; } return count; } 由于这种方法用到了模除运算,所以这个方法只能处理

一个数的二进制表示中1的个数——10

实现一个函数,输入一个整数,输出该数二进制表示中1的个数.例如,将9表示成二进制为1001,有2位是1,因此如果输入数字9,该函数输出2. 如果让我们将一个十进制的数转换成二进制的表示,我们就会不停的模除模除2取它的余数,因此,就可以用这样的方法解决: #include <iostream> using namespace std; size_t count_one_num(int n) {     size_t count = 0;     while(n != 0)     {      

输出一个数的二进制序列中1的个数(三种方法)

由于这个数有可能是负数,负数在计算机中以补码的方式存储,要求负数的补码中1的个数依然可以正确输出,方法如下: 1.定义这个数的变量类型为无符号整型(unsigned int) 代码为 include<stdio.h>int count_one_bits(unsigned value){int count=0;while(value){   if(value%2==1)   {count++;   }   value=value/2; }return count;}int main(){unsi

编程之美2.1 求二进制中1的个数

最近一段的时间,一直在看编程之美之类的算法书籍,刚开始看编程之美,感觉到难度太大,有时候也不愿意去翻动这本书,不过,经过一段时间的修炼,我也彻底的喜欢上这本书了, 书中的算法涉及到很多方面,树,链表,位运算,数组,hash表应用等等. 由于最近事情也忙得差不多了,我重新写了一遍编程之美中的算法,在这里记录下来,以便以后阅读方便. 第一道题从2.1写起,这道题目难度不是很大,首先,给出这个题目的函数声明: /*2.1 求二进制中1的个数*/ int DutCountOf1InBin_1(unsig

编程之美2——N!的二进制表示中最低位1的位置

任何数在计算机内部都是用二进制表示的,可以用这个特性来快速判断N!的二进制表示中最低位1的位置. 解法一: 将一个数的二进制数除以2,若二进制数的末尾是0,则能整除,否则不能整除. 因此,求 N!的二进制表示中最低位1的位置 即为求 N!中有多少个质因数2 以下为代码1: #include <iostream> using namespace std; int main(void) { int n,m; m=0; cin>>n; while(n) { n>>=1; m+

编程之美2.13 子数组最大乘积

问题描述: 给定一个长度为N的整数数组,只允许用乘法,不能用除法,计算任意(N-1)个数的组合乘积中最大的一组,并写出算法的时间复杂度. 解法: 1.暴力解法------O(n^2) 2.前后缀法------O(n) 3.统计法--------O(n) 具体思路和代码: 1.暴力解法: 思路:利用两层循环,依次删掉一个,其余的做乘法,计算出最大的. 代码: 1 int s1(int A[], int n) 2 { 3 int s = 1; 4 int max; 5 for(int i = 1;

Java 编程之美:并发极速赛车平台出租编程高级篇

借用 Java 并发极速赛车平台出租haozbbs.comQ1446595067 编程实践中的话:编写正确的程序并不容易,而编写正常的并发程序就更难了. 相比于顺序执行的情况,多线程的线程安全问题是微妙而且出乎意料的,因为在没有进行适当同步的情况下多线程中各个操作的顺序是不可预期的. 并发编程相比 Java 中其他知识点学习起来门槛相对较高,学习起来比较费劲,从而导致很多人望而却步: 而无论是职场面试和高并发高流量的系统的实现却都还离不开并发编程,从而导致能够真正掌握并发编程的人才成为市场比较迫

编程之美2.14 求数组的子数组之和的最大值

问题描述: 一个有N个整数元素的一维数组(A[0], A[1], A[2],...,A[n-1]),这个数组当然有很多子数组,那么子数组之和的最大值是什么呢? 解法: 1. 暴力解法-------O(N^3) 2. 改进版暴力解法-------O(N^2) *3. 分治算法-------O(NlogN)(暂时未去实现) 4. 数组间关系法-------O(N) 具体思路和代码: 1.暴力解法 思路:Sum[i,...,j]为数组第i个元素到第j个元素的和,遍历所有可能的Sum[i,...,j].

编程之美2.17 数组循环移位

问题描述: 设计一个算法,把一个含有N元素的数组循环左移或者右移K位. 解决方法: 1. 暴力解法------O(KN) 2. 颠倒位置------O(N) 具体思路和代码: 1. 暴力解法------O(KN) 思路:循环K次,每次移动一位 代码: 1 //右移 2 void s1(int A[], int n, int k) 3 { 4 k = k % n; 5 for(int i = 0; i < k; i++) 6 { 7 int t = A[n-1]; 8 for(int j = n-