51.和为 n 连续正数序列(数组)。
题目:输入一个正数 n,输出所有和为 n 连续正数序列。
例如输入 15,由于 1+2+3+4+5=4+5+6=7+8=15,所以输出 3 个连续序列 1-5、 4- 6 和 7-8。
分析:这是网易的一道面试题。
一道简单的小题
/* 51.和为 n 连续正数序列(数组)。 题目:输入一个正数 n,输出所有和为 n 连续正数序列。 例如输入 15,由于 1+2+3+4+5=4+5+6=7+8=15,所以输出 3 个连续序列 1-5、 4- 6 和 7-8。 分析:这是网易的一道面试题。 */ #include <stdio.h> //思路:设连续数字中首个数字为 s 连续数字个数为 l //则这些数字的和为 s*l + l*(l-1)/2 void find(int n) { int l; int s; for(s = 1; s * 2 + 1 <= n; s++) //首个数字循环 { for(l = 1; s * l + (l *(l - 1))/2 <= n; l++) { if(s * l + (l *(l - 1))/2 == n) { for(int i = s; i < l + s; i++) { printf("%d ", i); } printf("\n"); } } } } int main() { find(30000154); return 0; }
网上看到一个思路更好的, 其实没有必要对s循环的,根据l直接算s就可以了。
http://blog.csdn.net/wumuzi520/article/details/8046201
那么
a1+a2+...+ak=n
因为连续,所以
a1+(a1+1)+(a1+2)+...+(a1+k-1)=n
即
k*a1+k(k-1)/2=n
这样就可以求得
a1=(n-k(k-1)/2)/k
a1即为连续数中的最小值,只有在a1为整数的情况下才会符合要求,即
(n-k(k-1)/2)%k==0
时才符合要求。
对符合要求的a1连续打印k个递增(公差为1)的值即可。
#include <iostream> #include <cmath> using namespace std; void Sequence1(int n) { int M = (sqrt(8*n+1)-1)/2; for(int i = 2; i <= M; i++) { if((n-(i-1)*i/2)%i == 0) //!!!!!注意学习这里 { int nMin = (n-(i-1)*i/2)/i; for(int j = 0; j < i; j++) { cout << nMin++ << " "; } cout << endl; } } }