方法の一つ:動的計画
詳細については、している億内のすべての素数を見つけると、どのようにそれ最速行うには-ほとんど知っていますか?。
次のコードは、Pythonのちょうどレプリカバージョンです
時間の複雑さはおよそ$ O(N ^ \ FRAC {3} {4})$ですが、私のコンピュータでスパイシーなチキン4Sを使って
#include <ビット/ STDC ++ H> 使用して 名前空間STDを、 typedefの長い 長いLL。 const int型 MAXN = 2E5 + 10 。 INT V [MAXN]。 マップ < int型、LL> S; LL合計(LLのN) { int型、M =(INT )SQRT(N) INT、T = N / M。 用(int型 I = 1 ; I <= M; I ++)はV [I- 1 ] = N / I。 int型 CNT = 1 ; 以下のために(int型 I = T + Mを-2、I> = M; i--)V [I] = CNT ++ 。 以下のために(int型 i = 0 ; iが<= T + M- 2 ; iは++)S [V [I]] = 1LL * V [I] *(V [I] + 1)/ 2 - 1 。 用(INT P = 2 ; p <= Mであり; p ++ ) { 場合(S [P]> S [P- 1 ]) { LL SPの =のS [P- 1 ]。 LL P2 = P * P; 以下のために(int型私= 0 ; I <= T + M- 2、I ++) { LLのV = V [i]は、 もし(V <P2) ブレーク。 S [V] - = P×(S [V / P] - SP)。 } } } 戻りS [N]。 } int型のmain() { のprintf(" %LLDする\ n "、合計(1000000000 ))。 }
方法2:エッペンドルフふるいです
アイデアは、すべての素数を遮蔽して、コメントを追加、非常に簡単です。
私のコンピュータの23Sで使用する場合、時間の複雑さは、$ O(nloglogn)$です。
#include <ビット/ STDC ++ H> 使用して 名前空間STDを、 typedefの長い 長いLL。 const int型 MAXN = 1E9 + 10 。 BOOL VIS [MAXN ]。 LL篩(int型N) { LL RET = 0 。 INT、M =(INT)SQRT(N + 0.5 )。 用(int型 iは= 2 ; I <= M Iは++)場合(!VIS [I]) { ため(int型 J =私を*; J <= N; J + = I)VIS [j]は= 真; RET + = I; } のために(int型 iがm + = 1 ; iがn = <; I ++の) 場合(!VIS [I]) RET + = I。 リターンRET; } int型のmain() { のprintf(" %LLDする\ n "、ふるい(1000000000 ))。 リターン 0 ; }