CODEFORCES, 450E Jzzhu and Apples <筛素数>

来源:互联网 发布:windows 8.1K 编辑:程序博客网 时间:2024/04/27 19:16

题目:http://codeforces.com/problemset/problem/450/E

题意:从果树上摘果子,果子编号1~n,要把果子打包卖给水果店,每个包裹不该少于两个果子,每个包裹中的果子互相不互质,求最多打包多少个,及分别求出每个包裹内的编号(若有多种情况,输出一种即可)

分析:素数  不互质:公约数不为1n<=10^5

思路:先对n个数进行筛素数,然后从素数较大的开始组合,选素数的倍数的数形成一列数,若总数为奇数则剔除素数两倍的数。其他各数两两匹配,并做好访问过的标记

#include <iostream>#include <cstdio>#include <cstring>#include <vector>#include <utility>using namespace std;const int MAXN = 1e+5;int p_exp[MAXN];bool vis[MAXN];void PRIME(int n){    memset(p_exp,0,sizeof(p_exp));    memset(vis,false,sizeof(vis));    for(int i =2;i*i<=n;i++)    {        if(p_exp[i])            continue;        for(int j=i*i;j<=n;j+=i)        {            p_exp[j] = 1;        }    }}int main(){    int n;    scanf("%d",&n);    PRIME(n);    vector<pair<int,int> > vv_pai;    vector<int> g;    for(int i = n/2;i>1;i--)    {        if(p_exp[i])            continue;        g.clear();        for(int j=i;j<=n;j+=i)        {            if(vis[j]) continue;            g.push_back(j);        }        if(g.size()&1)            swap(g[1],g[g.size()-1]);        for(unsigned int j=0;j<g.size()-1;j+=2)        {            vv_pai.push_back(make_pair(g[j],g[j+1]));            vis[g[j]] =true;vis[g[j+1]] = true;        }    }    printf("%u\n",vv_pai.size());    for(unsigned int i=0;i<vv_pai.size();i++)    {        printf("%d %d\n",vv_pai[i].first,vv_pai[i].second);    }    return 0;}


0 0
原创粉丝点击