// 已知连续正整数数列{ K } = K1, K2, K3...Ki的各个数相加之和为S,i = N(0 < S < 100000, 0 < N < 100000), 求此数列K。
// 输入描述:输入包含两个参数,1)连续正整数数列和S,2)数列里数的个数N。
// 输出描述:如果有解输出数列K,如果无解输出 - 1
// 示例1:
// 输入:525 6
// 输出:85 86 87 88 89 90
#include <iostream>
#include <vector>
#include <functional>
#include <algorithm>
using namespace std;
/**
* 寻找连续正整数数列,使得数列元素之和为给定值 sum
* @param sum 给定的数列之和
* @param n 数列的长度
* @return 满足条件的连续正整数数列,如果不存在则返回空向量
*/
vector<int> solve(int sum, int n)
{
// 初始化左右指针
int left = 1;
int right = sum;
// 使用二分法搜索
while (left <= right)
{
// 计算中点
int mid = (left + right) / 2;
// 计算以 mid 为起点的 n 个连续正整数的和
int mr = mid + n - 1;
int s = (mid + mr) * n / 2;
// 如果和等于给定值,说明找到满足条件的数列
if (s == sum)
{
// 构造并返回结果数列
vector<int> res;
for (int i = mid; i <= mr; i++)
{
res.push_back(i);
}
return res;
}
// 如果和大于给定值,说明需要缩小数列范围
else if (s > sum)
{
right = mid - 1;
}
// 如果和小于给定值,说明需要扩大数列范围
else
{
left = mid + 1;
}
}
// 如果没有找到满足条件的数列,返回空向量
return {};
}
int main()
{
int S = 0;
int N = 0;
while (1)
{
// 输入数列总和和数列长度
cout << "请输入数列总和:";
cin >> S;
if (S != -1)
{
cout << "请输入数列个数:";
cin >> N;
// 调用solve函数,获取结果数列
vector<int> test = solve(S, N);
// 输出结果
if (test.size() == 0)
{
cout << "-1" << endl;
}
else
{
for_each(test.begin(), test.end(), [](int a) {cout << a << " "; });
cout << endl;
}
}
else
break;
}
return 0;
}