ignatius 喜歡收集蝴蝶標本和郵票,但是eddy的愛好很特別,他對數字比較感興趣,他曾經一度沉迷於素數,而現在他對於一些新的特殊數比較有興趣。
這些特殊數是這樣的:這些數都能表示成m^k,m和k是正整數且k>1。
正當他再度沉迷的時候,他發現不知道什麼時候才能知道這樣的數字的數量,因此他又求助於你這位聰明的程式設計師,請你幫他用程式解決這個問題。
為了簡化,問題是這樣的:給你乙個正整數n,確定在1到n之間有多少個可以表示成m^k(k>1)的數。
input
本題有多組測試資料,每組包含乙個整數n,1<=n<=1000000000000000000(10^18).
output
對於每組輸入,請輸出在在1到n之間形式如m^k的數的總數。
每組輸出佔一行。
題解: 由於2^60>1^18 故最初想法是列舉n的2~60次方根容斥.
注意到a^mn = (a^m)^n, 剩下a^m的n次項總可以令n為質數,故直接列舉[2, 60] 的質數即可.
又注意到有些數字可能被重複計算. 例如3^15這個數在3次方根內已經計算過, 在5次方根又被計算過一次.
於是這題的想法就完成了: 以60以內的質數為基. 進行容斥.
原始碼:#include#include#include#include#include#include#include#include#include#include#include#includeusing namespace std;
typedef long long ll;
typedef pairp;
const int inf = 0x7fffffff;
const int max_n = 60;
const int max_v = 0;
const int max_m = 0;
const int max_q = 0;
void show(string a, int val)
} int sym = num&1? 1: -1;
ll tmp = (ll)(pow(n, 1.0/k)+eps);
res += tmp*sym;
} return res;
}int main(){
p = sieve(60);
while(cin>>n){
cout<
hdu 2204 Eddy s愛好 容斥
根據指數的質數分解進行容斥 比如 k a 3 且 k b 5,那麼 k c 15 所以 a 的可選個數 加 b的可選個數減去c的可減個數就是總的個數了因為 a 3和b 5有重複的 include include include include include include define ll lo...
HDU 2204 Eddy s愛好 容斥
input 本題有多組測試資料,每組包含乙個整數n,1 n 1000000000000000000 10 18 output 對於每組輸入,請輸出在在1到n之間形式如m k的數的總數。每組輸出佔一行。sample input 10 361000000000000000000sample output...
hdu2204 Eddy s愛好(容斥)
題意 給定n,問有多少個p m k,滿足p n 要求m 1,k 1 資料範圍 n 1e18 解法 顯然列舉m肯定不行,因為m 2 1e18 那麼m 1e9,考慮列舉k,2 60 1e18 因此列舉k最多列舉60個,如果k是乙個合數,那麼k可以拆分為乙個數與質數的乘積 k x p,那麼m k可以變為m...