Codeforces 432C
题意:
给出一个长度为n(n<=10^5)的数组a, 数组a是数字1到n的一种排列(打乱顺序).
每次可以选择两个数(不同)进行交换, 但是交换的条件是被选择的两个数的下标之差加1应该是一个素数.
思路:
比赛的时候WA到爆..好弱, 思路基本都是对的, 贪心. 用数组pos[i]来维护值i在数组中的位置.
对于第i个数, 如果 pos[i]-i+1是素数,那么就直接交换.否则, 需要多次交换来使得a[i] = i;
采用贪心策略, 从i+1开始枚举是否可以与pos[i]进行交换, 这里交换的次数不会很多,
因为只有当m!+2, m!+3, ......., m!+m时会存在m-1个连续的合数, 而n<=10^5, 所以m <=8
所以交换的次数不会超过5次.
附上代码:
/*************************************************************************
> File Name: C.cpp
> Author: Stomach_ache
> Mail: sudaweitong@gmail.com
> Created Time: 2014年05月15日 星期四 23时51分15秒
> Propose:
************************************************************************/ #include <cmath>
#include <string>
#include <cstdio>
#include <vector>
#include <fstream>
#include <cstring>
#include <iostream>
#include <algorithm>
using namespace std; bool is_prime[];
int a[], pos[]; // hold the index of the value of i
typedef pair<int, int> pii;
vector<pii> ans; // keep each move... void
init() {
memset(is_prime, true, sizeof(is_prime));
is_prime[] = false;
for (int i = ; i < ; i++) {
if (is_prime[i]) {
for (int j = i*i; j < ; j += i) {
is_prime[j] = false;
}
}
}
return ;
} int
main(void) {
init();
int n;
scanf("%d", &n);
for (int i = ; i <= n; i++) {
scanf("%d", a + i);
pos[a[i]] = i;
}
for (int i = ; i <= n; i++) {
if (i == a[i]) continue;
if (is_prime[pos[i]-i+]) {
swap(a[i], a[pos[i]]);
ans.push_back(pii(pos[i], i));
pos[a[pos[i]]] = pos[i];
pos[i] = i;
} else {
// distance from index i to pos[i]
int d = pos[i] - i;
// in other words, a[i] will be equal to i when d equals 0
while (d) {
for (int k = d; k >= ; k--) {
if (is_prime[k+]) {
// from index of i+d-k to index of pos[i]
swap(a[i+d-k], a[pos[i]]);
// push to ans
ans.push_back(pii(i+d-k, pos[i]));
// update pos[]
pos[a[pos[i]]] = pos[i];
pos[i] = i+d-k;
// update d
d -= k;
break;
}
}
}
}
}
// for (int i = 1; i <= 10; i++) {
// cout << a[i] << ' ';
// }
// cout << endl;
int len = ans.size();
printf("%d\n", len);
for (int i = ; i < len; i++) {
if (ans[i].first > ans[i].second) {
swap(ans[i].first, ans[i].second);
}
printf("%d %d\n", ans[i].first, ans[i].second);
} return ;
}
Codeforces 432C的更多相关文章
- CodeForces 432C Prime Swaps
Description You have an array a[1], a[2], ..., a[n], containing distinct integers from 1 to n. Your ...
- python爬虫学习(5) —— 扒一下codeforces题面
上一次我们拿学校的URP做了个小小的demo.... 其实我们还可以把每个学生的证件照爬下来做成一个证件照校花校草评比 另外也可以写一个物理实验自动选课... 但是出于多种原因,,还是绕开这些敏感话题 ...
- 【Codeforces 738D】Sea Battle(贪心)
http://codeforces.com/contest/738/problem/D Galya is playing one-dimensional Sea Battle on a 1 × n g ...
- 【Codeforces 738C】Road to Cinema
http://codeforces.com/contest/738/problem/C Vasya is currently at a car rental service, and he wants ...
- 【Codeforces 738A】Interview with Oleg
http://codeforces.com/contest/738/problem/A Polycarp has interviewed Oleg and has written the interv ...
- CodeForces - 662A Gambling Nim
http://codeforces.com/problemset/problem/662/A 题目大意: 给定n(n <= 500000)张卡片,每张卡片的两个面都写有数字,每个面都有0.5的概 ...
- CodeForces - 274B Zero Tree
http://codeforces.com/problemset/problem/274/B 题目大意: 给定你一颗树,每个点上有权值. 现在你每次取出这颗树的一颗子树(即点集和边集均是原图的子集的连 ...
- CodeForces - 261B Maxim and Restaurant
http://codeforces.com/problemset/problem/261/B 题目大意:给定n个数a1-an(n<=50,ai<=50),随机打乱后,记Si=a1+a2+a ...
- CodeForces - 696B Puzzles
http://codeforces.com/problemset/problem/696/B 题目大意: 这是一颗有n个点的树,你从根开始游走,每当你第一次到达一个点时,把这个点的权记为(你已经到过不 ...
随机推荐
- PAT甲级——A1063 Set Similarity
Given two sets of integers, the similarity of the sets is defined to be /, where Nc is the number ...
- PAT甲级——A1056 Mice and Rice
Mice and Rice is the name of a programming contest in which each programmer must write a piece of co ...
- Hadoop集群中有哪些节点类型
- Gradle:gradle下载插件
https://github.com/michel-kraemer/gradle-download-task 用法在readme中已经讲的很清楚了,我主要介绍下注意事项吧. 我用这个插件的目的是为了让 ...
- Vue-cli3.x在开发环境中(router采用 history模式)出现Failed to resolve async component default: Error: Loading chunk {/d} failed.或者Uncaught SyntaxError: Unexpected token <错误
使用Vue-cli3.x开发环境中(router采用 history模式)出现Failed to resolve async component default: Error: Loading chu ...
- PHP--时间格式处理
Ymd格式转Y-m-d或转成时间戳将Ymd格式如19930811转成1993-08-11格式 date('Y-m-d',strtotime('19930811') 将Ymd格式如19930811转成时 ...
- WWDC 上讲到的 Objective C / LLVM 改进
https://developer.apple.com/wwdc/videos/ Advances in Objective-C What's New in the LLVM Compiler 下面是 ...
- C# 多线程的代价~内存都被吃了!
异步操作是.net4.5推出的新名词,事实上,这东西早就有了,它归根结底是通过线程池来实现的,即将一个大任务分成多个小任何块,每个线程并行处理其中的一个,完成后再把结果告诉主线程,在.net4.5推出 ...
- Ubuntu 16.04 LTS安装Docker最新版
一.安装Docker的先决条件 1.运行64位CPU构架的计算机(目前只能是x86_64和amd64),请注意,Docker目前不支持32位CPU.2.运行Linux 3.8或更高版本内核.一些老版本 ...
- jnhs-springmvc 请求组合不正确,比如请求路径出现两次
初学springmvc 向后台传参数,结果发现,一直404 404后没有路径,说明 没有进入controller 仔细一看,请求路径不对,重复出现 页面是这样写的 页面是这样写的 原因是,请求链接和当 ...