1. 程式人生 > >bzoj2190 [SDOI2008]儀仗隊

bzoj2190 [SDOI2008]儀仗隊

bsp solved sam scu 否則 就會 ++ 數據 告訴

2190: [SDOI2008]儀仗隊

Time Limit: 10 Sec Memory Limit: 259 MB
Submit: 3353 Solved: 2168
[Submit][Status][Discuss]

Description

  作為體育委員,C君負責這次運動會儀仗隊的訓練。儀仗隊是由學生組成的N * N的方陣,為了保證隊伍在行進中整齊劃一,C君會跟在儀仗隊的左後方,根據其視線所及的學生人數來判斷隊伍是否整齊(如下圖)。    技術分享   現在,C君希望你告訴他隊伍整齊時能看到的學生人數。

Input

  共一個數N。

Output

  共一個數,即C君應看到的學生人數。

Sample Input

  4

Sample Output

  9


HINT

【數據規模和約定】   對於 100% 的數據,1 ≤ N ≤ 40000

分析:如果以C君所在的點為原點來建立坐標系,那麽只有x,y互素才能被看到,否則就會被(x / gcd(x,y),y / gcd(x,y))擋住,計算互素的數的對數的經典做法就是利用歐拉函數,記錄1~i與i互素的點的個數然後*2就好了,在這道題裏我們求出∑φ(i) (2 <= i < n) ,答案*2+3就好了(還有0,1 1,0 1 1這三個點).
#include <cmath>
#include <cstdio>
#include 
<cstring> #include <iostream> #include <algorithm> using namespace std; int n,ans,phi[40010]; void getphi() { phi[1] = 1; for (int i = 2; i <= n; i++) if (!phi[i]) for (int j = i; j <= n; j+=i) { if (!phi[j]) phi[j] = j; phi[j] = phi[j] / i * (i - 1
); } } int main() { scanf("%d",&n); getphi(); for (int i = 2; i < n; i++) ans += phi[i]; printf("%d\n",ans * 2 + 3); return 0; }

bzoj2190 [SDOI2008]儀仗隊