CF 450E Jzzhu and Apples 数学+模拟

E. Jzzhu and Apples
time limit per test
1 second
memory limit per test
256 megabytes
input
standard input
output
standard output

Jzzhu has picked n apples from his big apple tree. All the apples are numbered from 1 to n. Now he wants to sell them to an apple store.

Jzzhu will pack his apples into groups and then sell them. Each group must contain two apples, and the greatest common divisor of numbers of the apples in each group must be greater than 1. Of course, each apple can be part of at most one group.

Jzzhu wonders how to get the maximum possible number of groups. Can you help him?

Input

A single integer n (1 ≤ n ≤ 105), the number of the apples.

Output

The first line must contain a single integer m, representing the maximum number of groups he can get. Each of the next m lines must contain two integers — the numbers of apples in the current group.

If there are several optimal answers you can print any of them.

Examples
input
Copy
6
output
Copy
2
6 3
2 4
input
Copy
9
output
Copy
3
9 3
2 4
6 8
input
Copy
2
output
Copy
0

题目要求的是在1-n范围内最多有多少对数的最大公约数大于1
因为要求最大,所以偶数对和奇数对要尽量不凑成对
考虑到加双倍后奇数任然是奇数,所以我们可以通过加倍的方式找出公约数大于1的对数
然后就是细节的处理了

#include<algorithm>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<cstdio>
#include<string>
#include<vector>
#include<cmath>
#define debug(a) cout << #a << " " << a << endl
using namespace std;
typedef long long ll;
const ll mod = 1e9 + 7;
const ll maxn = 1e5 + 10;
ll vis[maxn], is[maxn];
vector<ll> a;
vector< pair< ll, ll > > E;
int main() {
    std::ios::sync_with_stdio(false);
    ll n;
    while( cin >> n ) {
        memset( vis, 0, sizeof(vis) );
        memset( is, 0, sizeof(is) );
        E.clear();
        for( ll i = 4; i <= n; i += 2 ) {
            vis[i] = 1;
        }
        for( ll i = 3; i <= n; i += 2 ) { //找出奇数的倍数
            if( !vis[i] ) {
                if( i*2 > n ) {
                    break;
                }
                a.clear();
                for( ll j = i; j <= n; j += 2*i ) {
                    vis[j] = 1;
                    if( !is[j] ) {
                        is[j] = 1;
                        a.push_back(j);
                    }
                }
                for( ll j = a.size()-1; j > 0; j -= 2 ) {
                    E.push_back( make_pair( a[j], a[j-1] ) );
                    is[a[j]] = is[a[j-1]] = 1;
                }
                if( a.size() & 1 ) { //如果有单独无法找到配对的奇数,用他的而倍数与之配对
                    E.push_back( make_pair( a[0], a[0]*2 ) );
                    is[a[0]] = is[a[0]*2] = 1;
                }
            }
        }
        if( n & 1 ) {
            n --;
        }
        ll flag = 0, t;
        for( ll i = n; i > 0; i -= 2 ) { //除去奇数后剩余的偶数对
            if( !is[i] ) {
                if( !flag ) {
                    flag = 1;
                    t = i;
                } else {
                    flag = 0;
                    E.push_back( make_pair( i, t ) );
                }
            }
        }
        cout << E.size() << endl;
        for( ll i = 0; i < E.size(); i ++ ) {
            cout << E[i].first << " " << E[i].second << endl;
        }
    }
    return 0;
}

 

posted on 2018-05-10 11:38  九月旧约  阅读(132)  评论(0编辑  收藏  举报

导航