题意:
输入正整数n和k(1<=n,k<=),计算
分析:
根据紫书,假设k/i的整数部分等于p,则k mod i=k-i*p。于是从i,i+1,i+2,······,j,k除以它们的商的整数部分都相同,则k除以它们的余数会是一个等差数列。
这样,可以在枚举i时把它所在的等差数列之和累加到答案中。这需要计算满足[k/j]和[k/i]=p的最大j。
当p=0时这样的j不存在,所以等差数列一直延续到序列的最后。
当p>0时j为满足k/j>=p的最大j,即j<=k/p。
注意:当i>k时k mod i = k。即i>k的部分之和为k*(n-k)。
代码:
#include<iostream>
using namespace std;
typedef long long ll;
ll ans,n,k;
void f(){
ll i=2,p,t,d,nn;
ans=0;
while(i<k){
if(i>n)
break;
p=k/i;
t=k%i;
d=k/p;
//printf("i:%d p:%d t:%d d:%d ",i,p,t,d);
nn=min(d,n)-i+1;
ans+=nn*t+((k%(i+1)-t)*(nn-1)*nn)/2;
//printf("%d\n",(d-i+1)*t+(k%(i+1)-t)*(d-i));
i=min(d,n)+1;
}
if(n>k){
ans+=k*(n-k);
}
}
int main(){
while(cin>>n>>k){
f();
cout<<ans<<endl;
}
return 0;
}