CSU-2214 Sequence Magic

题目链接

http://acm.csu.edu.cn:20080/csuoj/problemset/problem?pid=2214

题目

Description

有一个1到N的自然数序列1,2,3,...,N-1,N。

我们对它进行M次操作,每次操作将其中连续的一段区间 [Ai,Bi][Ai,Bi] (即第Ai个元素到第Bi个元素之间的一段)取出,然后插入到剩下的第Ci个元素的后面,如果Ci=0,表示插入到最左端。

现在,M次操作完后,有K个询问,每个询问Pi表示询问最终第Pi个元素是几。你的任务是写一个程序,依次回答这K个询问。

Input

第一行三个数,N,M,K。

接下来M行,每行三个整数Ai,Bi,Ci。

接下来K行,每行一个正整数Pi。

1<=N<=\(10^9\),1<=M<=\(10^4\),1<=K<=1000,1<=Ai<=Bi<=N,0<=Ci<=N-(Bi-Ai+1),1<=Pi<=N;

Output

输出共K行,为每次询问的答案。

Sample Input

13 3 13 
6 12 1 
2 9 0 
10 13 8 
1 
2 
3 
4 
5 
6 
7 
8 
9 
10 
11 
12 
13

Sample Output

6 
7 
8 
9 
10 
11 
12
2 
3 
4 
5 
13 
1 

题解

由于k,m都很小,所以我们可以考虑离线的思想离线的思想,对于每一次询问,从m到1把区间平移操作恢复。我们要知道的是最后序列的第x个数,那么我们可以算出不做最后一次平移前x是第几个位置,这样倒退到第一次就是一开始x所在的位置,也就是x所对应的数,输出答案即可。

考虑一下怎么算,有两种情况\(c[j] \ge a[j]\)时,我们把\(a[j]...b[j]\)移动到\(c[j]\)后面,此时若x在\(a[j],c[j]\)之间,那么他就会向后移动\(b[j]-a[j]+1\)个数,如果它在\(c[j]+1,c[j]+b[j]-a[j]+1\)之间,那么设这次位置是x,恢复平移后位置为y,那么\(a[j]+(x-c[j])-1=y\),即x+=a[j]-c[j]-1。其他情况x不变

\(c[j]<a[j]\),此时若x在\(c[j]+1,c[j]+b[j]-a[j]+1\)之间,那么x+=a[j]-c[j]-1,若x处在\(c[j]+1+b[j]-a[j]+1,b[j]\)之间,那么\(x=c[j]+x-(c[j]+b[j]-a[j]+1)\)即x+=a[j]-b[j]-1。

一直倒推到1即为答案,依次输出即可

AC代码

#include<bits/stdc++.h>
#define N 10050
using namespace std;
int a[N], b[N], c[N];
typedef long long ll;
int main() {
	int n, m, k;
	scanf("%d%d%d", &n, &m, &k);
	for (int i = 1; i <= m; i++) {
		scanf("%d%d%d", &a[i], &b[i], &c[i]);
	}
	for (int i = 1; i <= k; i++) {
		ll x;
		scanf("%lld", &x);
		for (int j = m; j >= 1; j--) {
			if (c[j] >= a[j]) {
				if (x >= a[j] && x <= c[j]) {
					x += b[j] - a[j] + 1;
				}
				else if (x >= c[j] + 1 && x <= c[j] + b[j] - a[j] + 1) {
					x += a[j] - c[j] - 1;
				}
			}
			else {
				if (x >= c[j] + 1 && x <= c[j] + b[j] - a[j] + 1) {
					x += c[j] + 1 + a[j] - c[j] - 1 - 1 - c[j];
				}
				else if (x >= c[j] + b[j] - a[j] + 1 + 1 && x <= b[j]) {
					x -= (b[j] - a[j] + 1);
				}
			}
		}
		printf("%d\n", x);
	}
}
/**********************************************************************
	Problem: 2214
	User: Artoriax
	Language: C++
	Result: AC
	Time:284 ms
	Memory:2140 kb
**********************************************************************/

结语

至此所有寒假集训选拔写过的题的题解补完了,赶快开始补寒假集训的题解了,不能再划水了

posted @ 2019-02-14 00:29  Artoriax  阅读(168)  评论(0编辑  收藏  举报