1. 程式人生 > >Codeforces 822D My pretty girl Noora(數論)

Codeforces 822D My pretty girl Noora(數論)

view using cout prim pretty space actor true 因子

題目大意:一場選美比賽有N個人,可以分成N/x,每組x人。每組的比較次數為x(x-1)/2,f[N]為最後決出冠軍所需的比較次數,可以通過改變x的值使f[N]改變。題目給出t,l,r(1?≤?t?<?109?+?7,?2?≤?l?≤?r?≤?5·106)。求 t^0?f(l)+t^1?f(l+1)+?+t^r?l?f(r) 的最小值對1e9+7的模。

解題思路:①如果人數為素數,那f[N]=N(N-1)/2;

     ②如果不是素數,那就找出最小素因子x,分成N/x,每組x人,f[N]=N/x*f[x]+f[N/x]。

     關於②,比如6可以分為3個2或者2個3,所需比較數分別是5和7,顯然分的組數越多越好。還有關於為什麽加上f[N/x],因為是遞推的,所以f[N/x]肯定也是最小的,不用擔心N/x不是素數還要在進行分組的問題。

代碼:

 1 #include<iostream>
 2 using namespace std;
 3 typedef long long ll;
 4 const int N=5e6+5;
 5 const ll MOD=1e9+7; 
 6 bool prime[N];
 7 ll p[N];
 8 ll f[N];
 9 int cnt;
10 //素數表 
11 void is_prime(){
12     for(int i=2;i<=N;i++)
13         prime[i]=true;
14     for(int i=2;i*i<=N;i++){
15 if(prime[i]){ 16 p[cnt++]=i; 17 for(int j=i*i;j<=N;j+=i){ 18 prime[j]=false; 19 } 20 } 21 } 22 } 23 24 int main(){ 25 is_prime(); 26 f[1]=0; 27 for(int i=2;i<N;i++){ 28 //判斷是否為素數 29 if(prime[i]){
30 f[i]=((ll)i*(i-1)/2)%MOD; 31 } 32 else{ 33 //找最小素因子 34 ll factor; 35 for(int j=0;j<cnt;j++){ 36 if(i%p[j]==0){ 37 factor=p[j]; 38 break; 39 } 40 } 41 f[i]=(i/factor*f[factor]+f[i/factor])%MOD; 42 } 43 } 44 ll ans=0; 45 ll t,l,r; 46 cin>>t>>l>>r; 47 for(int i=r;i>=l;i--){ 48 ans=(ans*t)%MOD; 49 ans=(ans+f[i])%MOD; 50 } 51 cout<<ans<<endl; 52 }

Codeforces 822D My pretty girl Noora(數論)