2018NOIP第五次膜你赛

传送门

第一题 反蝴蝶效应

题意

有$n$个点,我们需要走过这些点仅$1$次,到点$i$时你的身上必须有$a_i$的能量。在那之后,你的能量会$-1$。求你开始时需要的最小能量值。

题解

算法一:二分。

算法二:输出$\max_{i=1}^{n}\left(a_i+i-1\right)$

input()
print(max(i+j  for i,j  in enumerate(map(int,input().split()))))

第二题 贝伦卡斯泰露

题意

给出一个长度为$n$的数列$A_i$,问是否能将这个数列分解为两个长度为$n/2$的子序列,满足

  • 两个子序列不互相重叠。
  • 两个子序列的数要完全一样,$\{1,2\}=\{1,2\},\{1,2\}\not=\{2,1\}$。

$T\leq 5,1\leq A_i\leq n\leq 40$,保证$n$为偶数。

题解

我太蒟蒻了,所以dfs水过了此题。。

#include <bits/stdc++.h>
#pragma GCC optimize (2)
using namespace std;

int n;
int a[45];
vector<int> v1, v2;

bool dfs(int x, int y) {
	if (y > n/2) return false;
	if (n-x+1+y < n/2) return false;
	for (int i=0; i<min(v1.size(), v2.size()); i++) if (v1[i] != v2[i]) return false;
	if (x == n+1) return y == n/2;
	v1.push_back(a[x]); if (dfs(x + 1, y + 1)) return true; v1.pop_back();
	v2.push_back(a[x]); if (dfs(x + 1, y)) return true; v2.pop_back();
	return false;
}

bool pre_spr() {
	/*int cnt[45];
	for (int i=1; i<=40; i++) cnt[a[i]]++;
	for (int i=1; i<=40; i++) if(cnt[a[i]] & 1) {
		n=2; a[1]=1;a[2]=2;
		return true;
	}*/
	return false;
}
bool do_spr(int x) {
	for (int i=1; i<=20; i++)
		if (a[i] != x) return false;
	n=20;
	for (int i=1; i<=20; i++) a[i]=a[i+20];
	return true;
}

int main() {
	//freopen("split.in", "r", stdin);
	//freopen("split.out", "w", stdout);
	int T; scanf("%d", &T);
	while (T--) {
		scanf("%d", &n);
		for (int i=1; i<=n; i++) scanf("%d", &a[i]);
		v1.clear(); v2.clear();
		if (!pre_spr() && n==40) for(int i=1; i<=40; i++) if(do_spr(i))break;
		if (!dfs(1, 0)) puts("Furude Rika");
		else puts("Frederica Bernkastel");
	}
	return 0;
}

第三题 形态形成场

先坑着

posted @ 2018-07-24 10:15  MCH__ds  阅读(132)  评论(0编辑  收藏  举报