题目简述:
给定一个整数n,对于1-n以内的数据,若存在一段连续的整数,相加和为n,则视为符合条件的整数。example:27: 2-7 ;8-10 ;13-14
解题思路:
对于n较小的数据,直接采用求所有和判断的方法:
大致思路如下:
:cin>>n;sum=0;
for(i=1;i<=n/2;i++){
for(sum=i,j=i+1;j<=n/2+1;j++){
sum+=j;
if(sum==n) output();
}
}
上述方法的时间复杂度为O(n^2),对于一些数据较大的输入处理十分耗时。当n=1000000时,运行时间就达到了几十上百秒。
从一下角度来对算法进行优化:
1.连续数据中的第一个数据最大为n/2。(第二个数据在其基础上+1,当n为偶数,和必>n,当n为奇数,这两个数刚好符合。)
2.对于刚好符合条件的sum==n,将第一个数与最后一个数据都+1;
-若sum>n,舍去第一个数;(数据超额,从小到大舍弃,避免遗漏)。
-若sum<n,将连续数据的最大数据+1.
代码如下:
#include<stdio.h>
#include<iostream>
#include<stdlib.h>
#include<time.h>
using namespace std;
int main(){
int n,t=0,i,j; //i,j分别代表第一个,最后一个数,t统计符合条件的组数,n为初始输入。
cin>>n;
i=1,j=2;
int sum=3; //sum为临时连续整数和。
clock_t start,finish;
start=clock();
while(i<=n/2){
if(i==j) break;
else if(sum==n){
cout<<i<<" "<<j<<endl;
sum-=i;
i++,j++,t++;
sum+=j;
}
else if(sum<n){
j++;
sum+=j;
}
else if(sum>n){
sum-=i;
i++;
}
}
finish=clock();
double total=(double)(finish-start)/CLOCKS_PER_SEC;
cout<<"总共有"<<t<<"对组合符合要求"<<endl;
cout<<"总共耗时(s):"<<total<<endl;
system("pause");
return 0;
}
在输入27 10000 1000000 100000000这4组数据下,查看程序运行效率:
n=27:
n=10000:
n=1000000:
n=100000000:
显而易见,效率提升较为明显对于所有范围内的int输入能够快速反应输出结果。