您的位置:首页 > 其它

Poj 2800 Joseph's Problem - 找规律

2013-08-24 10:55 429 查看
题目大意:给定n和k,求 ∑1<=i<=n(k
mod i)

题目分析:n和k很大,直接算会TLE,但是可以先打表找规律。(点击可见数学推导

               随便找几组数据可以发现下面的规律

                      1)如果k/i的值相等,那么kmodi的值成等差数列(连续的)

                      2)如果k比n大,那么k/i的值随i的值增大而减小

                      3)如果k比n小,那么kmodi 大于k,当i大于k时

               可见,主要解决的问题就是1),找到连续的成等差数列的区间。因为有规律3),所以不妨从后面往前找。如果发现了前面的规律,那么就会发现下                  面的规律:                 

                      4) 从后往前找,如果从j开始出现等差数列(j为等差数列第一项),那么该等差数列的最后一项为k/(k/j+1)+1 

               但是等差数列不一定出现,如果k/(k/j+1) >= j。

代码:

#include <stdio.h>
long long solve(int n,int k)
{
long long ans = 0;
if(n > k)
{
ans += (long long)(n-k) * k;
n = k;
}
int div = k/n;
while(n > 1)
{
int id = k/(div+1);
if(id >= n)
{
ans += k % n;
n--;
div = k/n;
continue;
}
int s = k%n;
int e = k%(id+1);
ans += (((long long )(s+e)*(n-id))>>1);
n = id;
div++;
}
return ans;
}
int main()
{
int n,k;
while(scanf("%d%d",&n,&k) != EOF) printf("%lld\n",solve(n,k));
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  数学