问题
输入一个整数,输出该数二进制表示中1的个数。其中负数用补码表示。
思路
方法一:就是让原始数据与1进行与运算,若为1,则表示最低位为1,则count++,原始数据向右移动1位。大概过程{1,0,0,1}&{1} --》 1 , {0,1,0,0}&{1}--》0, {0,0,1,0}&{1}--》0, {0,0,0,1}&{1}--》1,所以最后的结果为2。
方法二:方法二是对方法一的升级版,此方法并没有对number进行位运算,所以不存在方法一中的问题而且这个方法是有多少个1,进行多少次,而方法1是原始数据有多少位进行多少次。大概过程{1,0,0,1}&{1,0,0,0}--》{1,0,0,0},{1,0,0,0}&{0,1,1,1}--》{0,0,0,0}所以结果为2.
package offer010; import java.util.Scanner; /** * @Title: Main.java * @Package: offer010 * @Description 输入一个整数,输出该数二进制表示中1的个数。其中负数用补码表示。 * @author Han * @date 2016-4-19 下午2:02:24 * @version V1.0 */ public class Main { public static void main(String[] args) { Scanner scanner = new Scanner(System.in); long number = 0; int countOf1 = 0; while(scanner.hasNext()){ number = scanner.nextLong(); countOf1 = numberOf1Mehtod1(number); // countOf1 = numberOf1Mehtod2(number); System.out.println(countOf1); } } private static int numberOf1Mehtod1(long number) { int flag = 1; int count = 0; while(number > 0){ if((number & flag) == 1){ count++; } /** * 位运算 ==> number = number / 2,但是在效率上,位运算比除运算快很多,所以争取以后都用位运算替代除运算 * 对原始数据number进行了位运算,可以会出现问题,比如0x80000000的第一位表示的是负数时,做除法位运算,得到的结果应该是0xC0000000 * 最后会得到0xFFFFFFFF的死循环,所以最好不要对原始数据number进行位运算 */ number = number >> 1; } return count; } private static int numberOf1Mehtod2(long number) { int count = 0; while(number > 0){ /** * 此方法并没有对number进行位运算,所以不存在方法一中的问题 * 而且这个方法是有多少个1,进行多少次,而方法1是原始数据有多少位进行多少次 */ number = (number - 1) & number; count++; } return count; } }