[JSOI 2014]スマートステファニー

ポータル

[タイトル]背景

曇り夕方に車の窓
将来的には、待っている人持っている
権利を左に先読み
風水数曲がり来て、愛
の対話の種類を持って、私は会ったが
、私は彼が遠い将来にだ人が好き
、私は地下鉄からの風を聞くと、人々をハイ
私はナンバープレートの愛を保持並ん

説明[タイトル]

市の人々は常に、探し続けるマッチを保つが、誰がその人のように知らない、ナンバープレートを取りました。

しかし、ステファニーは、ステファニーは、ステファニーために数学を知っているように、同じではありません!それは、その後、彼らのナンバープレートの上に自分自身や他の人の手の正のナンバープレート番号のすべてをデジタルSを読み、S.にほぼ等しくなければなりませんと仮定します。ステファニーは、魔法のようなアルゴリズムを発見しました

ステファニーはそう常に(おい!これは本当にそれを飛ぶ)地下鉄や群衆の番号を探してナンバープレートを取ったが、彼女は彼らの他のすべてをすぐに見つけることがプログラムを書くためにあなたのことをお願いし忙しい歌「緑の光」でした人々。

入力フォーマット:

入力が含まれている\(K \)データのセットを。入力されたカード番号を含むデータの各セットのための\(S \)を

出力フォーマット:

各試験のために、2本の出力線は、最初の行は整数含ま\(m個\)を、発現(m個\)\のような人。
第二行は、対応含ま\(m個\)番号、等は、人のすべてのカード番号を表します。
注:出力ナンバープレートは、昇順に並べておく必要があります。

【入力】

42

【出力】

3
20 26 41

[分析]

コードは実際には、あるとして、Tacca自身の理解について書くためにここに、問題を解決するために兄をたくさん読んで、ほぼ全員の兄。
まず、ここでの唯一の分解定理を使用する:
\ [^ {N-P_1 = C_1とC_2} * {} * ^ P_2 ...... * P_Kは{C_Kは} ^ \]
があり除数:
= \ {私は\ [SUMをprod_ = 1} ^ {n}は{
\ sum_ {jは= 0} ^ {K} {P_I ^ J}} \] これらは実際に何もする必要があります。場合があります\(S-1 \)は素数で、その後、\(S-1 \)はナンバープレートなので、特別な文が必要です。検索(今\)\を見つけることが素数の積に相当し、\(\最終)添字素数検索、です\(左\)残りのために\(S \)

[コード]

#include<cstdio>
#include<cstdlib>
#include<algorithm>
#include<cstring>
#define maxn 60000
using namespace std;
int s;
int cnt=0,num;
int prime[maxn],ans[maxn];
bool flag[maxn];
void primes(){
    memset(flag,1,sizeof(flag));//筛素数
    flag[1]=0;
    for(int i=2;i<=maxn;i++){
        if(!flag[i]) continue;
        else{
            prime[++cnt]=i;
            for(int j=2;j*i<=maxn;j++)
                flag[i*j]=0;
        }
    }
}
bool is_prime(int x){//判断是否为素数
    if(x==1) return false;
    if(x==2) return true;
    for(int i=1;prime[i]*prime[i]<=x;i++)
        if(x%prime[i]==0) return false;
    return true;
}
void dfs(int now,int last,int left){//搜索
    if(left==1) {ans[++num]=now;return;}
    if(left-1>prime[last]&&is_prime(left-1)) ans[++num]=now*(left-1);
    for(int i=last+1;prime[i]*prime[i]<=left;i++)
        for(int j=prime[i]+1,k=prime[i];j<=left;k*=prime[i],j+=k)
            if(left%j==0)
                dfs(now*k,i,left/j);
}
int main(){
    primes();
    while(scanf("%d",&s)!=EOF){
        num=0;
        memset(ans,0,sizeof(ans));
        dfs(1,0,s);
        sort(ans+1,ans+1+num);//号码牌要按升序排列
        printf("%d\n",num);
        for(int i=1;i<=num;i++){
            printf("%d",ans[i]);
            if(i==num) printf("\n");
            else printf(" ");
        }
    }
    return 0;
}

おすすめ

転載: www.cnblogs.com/hlw1/p/11104874.html