编辑时间: 2015.8.20.16.40
注意: 目的只为 备忘。
一、阶乘
注: long 只能实现到15!, long long只能实现到20!,更大后续需用数组实现。
long long digui(int n)
{
if (1 >= n)
return 1;
else
return n*digui(n-1);
}
long long no_digui(int n)
{
int i = 0;
long long s = 1;
for(i = 1; i <= n; i++)
s=s*i;
return s;
}
二、 斐波那契
编辑时间:2015.8.22.11.00
注:1,1,2,3,5,8,13...... 形式的 数列。
int digui(int n)
{
if (2 >= n)
return 1;
return digui(n-1)+digui(n-2);
}
int no_digui(int n)
{
int old1 = 1, old2 = 1, s = 0, i = 0;
if (2 >= n)
return 1;
for(i = 3; i <= n; i++ )
{
s = old1 + old2; //其实还是 递归的原理, 列几个数, 分析一下, 就可以写出
old1 = old2; // old1是左边第一个,相当于n-2;old2左边第二个,相当于n-1。
old2 = s;
}
return s;
}
三、 1的个数统计
编辑时间:2015.8.27.9.30
注意:
1、只统计unsigned 型的;
2、unsigned 型的 移位 都是 逻辑移位(补0);
3、signed 型的移位左移(符号位 被干掉右边补0), 但右移要因编译器的不同而 结果不同(补0或者补符号位)。
unsigned int normal_count(unsigned int n)
{
unsigned int count = 0; //最寻常用法,不解释
while(0 < n)
{
if (n & 1) count++;
n>>=1;
}
return count;
}
unsigned int fast_count(unsigned int n) // 每次 消去 最右边的 1
{
unsigned int count;
for(count = 0; n ; count++)
n&=(n-1);
return count;
}
unsigned int good_idea_count(unsigned int n) // 比较 巧妙,但效率不一定高, 分析见下
{
n = (n & 0x55555555) + ((n>>1) & 0x55555555); // 相邻位 相加
n = (n & 0x33333333) + ((n>>2) & 0x33333333); // 相邻两位 相加
n = (n & 0x0f0f0f0f) + ((n>>4) & 0x0f0f0f0f); // 相邻四位 相加
n = (n & 0x00ff00ff) + ((n>>8) & 0x00ff00ff); // 相邻八位 相加
n = (n & 0x0000ffff) + ((n>>16) & 0x0000ffff); // 相邻16位 相加
// 但似乎默认了是32位,不知是否是诟病所在
return n;
}