题目1:二进制中1的个数
第二次还是采用C++,采用查表方式,由于C++的输入输出比较耗时,依然超时,换为C,Accepted,下边直接将C的代码给出。
下边给出4位一组的代码,待查数组小了,可是时间变长了,因为大数据需要更多地移位操作。
该题提交的第三次才通过了,最开始采用移位操作,会超时,后来改为查表,第一用C++写的,还是超时,无奈,改为C,通过,代码如下,有注释,这里就不在赘述了。
第一次采用C++移位操作,Time Limit Exceed。
/**
作者: 齐士垚
日期: 2013.6.23
功能: 计算一个数的二进制表示中含有的1的个数
语言: C++
*/
#include<iostream>
using namespace std;
int main() {
int i,n,m,count;
unsigned int flag; //尽量减少空间占用,采用unsigned int
while(cin>>n) { //扫描案例数目
for(i = 0; i < n; i++) {
count = 0; //重置计数器
flag = 1; //标志位,用于逐位判断数字是否为1
cin>>m; //输入待判数据
while(flag) { //循环直到判断完32位
if(m & flag) { //该位为1,计数器增1
count++;
}
flag <<= 1; //标志位移动
}
cout<<count<<endl; //输出计数值
}
}
return 0;
}
第二次还是采用C++,采用查表方式,由于C++的输入输出比较耗时,依然超时,换为C,Accepted,下边直接将C的代码给出。
/**
作者: 齐士垚
日期: 2013.6.23
功能: 计算一个数的二进制表示中含有的1的个数
语言: C
*/
#include<stdio.h>
int main() {
unsigned char table[256] = { //查表,表示8位二进制数总共含有1的个数,下标用该二进制数表示
//也可以4位一组,这样可以减小待查数组的大小,不过最后求结果的话,
//就麻烦了,有得必有失。
0,1,1,2, 1,2,2,3, 1,2,2,3, 2,3,3,4,
1,2,2,3, 2,3,3,4, 2,3,3,4, 3,4,4,5,
1,2,2,3, 2,3,3,4, 2,3,3,4, 3,4,4,5,
2,3,3,4, 3,4,4,5, 3,4,4,5, 4,5,5,6,
1,2,2,3, 2,3,3,4, 2,3,3,4, 3,4,4,5,
2,3,3,4, 3,4,4,5, 3,4,4,5, 4,5,5,6,
2,3,3,4, 3,4,4,5, 3,4,4,5, 4,5,5,6,
3,4,4,5, 4,5,5,6, 4,5,5,6, 5,6,6,7,
1,2,2,3, 2,3,3,4, 2,3,3,4, 3,4,4,5,
2,3,3,4, 3,4,4,5, 3,4,4,5, 4,5,5,6,
2,3,3,4, 3,4,4,5, 3,4,4,5, 4,5,5,6,
3,4,4,5, 4,5,5,6, 4,5,5,6, 5,6,6,7,
2,3,3,4, 3,4,4,5, 3,4,4,5, 4,5,5,6,
3,4,4,5, 4,5,5,6, 4,5,5,6, 5,6,6,7,
3,4,4,5, 4,5,5,6, 4,5,5,6, 5,6,6,7,
4,5,5,6, 5,6,6,7, 5,6,6,7, 6,7,7,8,
};
int i,n,m;
while(scanf("%d", &n) != EOF) { //直到待测案例结束
for(i = 0; i < n; i++) { //测试每组数据
scanf("%d", &m);
printf("%d\n",table[m & 0xff]
+ table[(m >> 8) & 0xff]
+ table[(m >> 16) &0xff]
+ table[(m >> 24) & 0xff]); //8位一组,求和作为结果
}
}
return 0;
}
下边给出4位一组的代码,待查数组小了,可是时间变长了,因为大数据需要更多地移位操作。
/**
作者: 齐士垚
日期: 2013.6.23
功能: 计算一个数的二进制表示中含有的1的个数
语言: C
*/
#include<stdio.h>
int main() {
unsigned char table[16] = { //查表,表示4位二进制数总共含有1的个数,下标用该二进制数表示
0,1,1,2, 1,2,2,3, 1,2,2,3, 2,3,3,4,
};
int i,n,m;
while(scanf("%d", &n) != EOF) { //直到待测案例结束
for(i = 0; i < n; i++) { //测试每组数据
scanf("%d", &m);
printf("%d\n",table[m & 0x0f]
+ table[(m >> 4) & 0x0f]
+ table[(m >> 8) &0x0f]
+table[(m >> 12) &0x0f]
+table[(m >> 16) &0x0f]
+table[(m >> 20) &0x0f]
+table[(m >> 24) &0x0f]
+ table[(m >> 28) & 0x0f]); //4位一组,求和作为结果
}
}
return 0;
}