acm2058[通俗易懂]

acm2058[通俗易懂]intmain(){   intn,m; intl,i,a,b,s; while(scanf(“%d%d”,&n,&m),n+m)  { l=(int)sqrt(2*m); for(i=l;i>=1;i–)    { s=(2*m+i-i*i)/2; if(s%i==0)     

大家好,又见面了,我是你们的朋友全栈君。如果您正在找激活码,请点击查看最新教程,关注关注公众号 “全栈程序员社区” 获取激活教程,可能之前旧版本教程已经失效.最新Idea2022.1教程亲测有效,一键激活。

Jetbrains全系列IDE稳定放心使用

int main(){     
int n,m; 
int l,i,a,b,s; 
while (scanf(“%d%d”,&n,&m),n + m)    

l = (int)sqrt(2 * m); 
for (i = l; i >= 1; i–)        

s = (2*m + i – i*i)/2; 
if(s % i == 0)           

a = s / i; 
if(a+i-1 > n) break; 
printf(“[%d,%d]\n”,a,a + i – 1); 


printf(“\n”);   

return 0; 
}  

最后,说一下我对代码的解释

假设:1,2,3,…,n中的i个数(a1,a2,…,ai)满足sum(a1,a2,…,ai)=m。

那么,1<=a1<=m,

当a1=1时,i=ai,i取得最大值,由于i*(1+i)/2=m,i=sqrt(2*m-i)<sqrt(2*m);

当a1=m时,i=1,i取得最小值。

所以,1<=i<=sqrt(2*m)。

同时我们知道,两个长度都为i却不相同的连续数列,它们的和不可能都等于m。

从上面的讨论可知,满足要求的数列的长度i在[1,sqrt(2*m)]之间,且不重复。

现在从sum(a1,a2,…,ai)=m反推,由于ai=a1+i-1,可知:

sum(a1,a2,…,ai) = (a1+ai)*i/2 = (a1+a1+i-1)*i/2= m

a1*i = (2*m+i-i*i)/2 = s

那么,存在1,2,3,…,n中的i个数(a1,a2,…,ai)满足sum(a1,a2,…,ai)=m,

等价于,对于s=(2*m+i-i*i)/2有:s%i=0(因为a1=s/i),且s/i+i-1<=n(因为ai=s/i+i-1)

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

发布者:全栈程序员-用户IM,转载请注明出处:https://javaforall.cn/186846.html原文链接:https://javaforall.cn

【正版授权,激活自己账号】: Jetbrains全家桶Ide使用,1年售后保障,每天仅需1毛

【官方授权 正版激活】: 官方授权 正版激活 支持Jetbrains家族下所有IDE 使用个人JB账号...

(0)


相关推荐

发表回复

您的电子邮箱地址不会被公开。

关注全栈程序员社区公众号