Codeforces Round #612 (Div. 1)A. Garland

A. Garland

题目链接-Garland
在这里插入图片描述
在这里插入图片描述
题目大意
给你1-n个数的乱序排列,有些位置上的数为0(即该位置为空),如何用剩下的数填充这个序列,使得相邻灯泡奇偶对数最小

解题思路
四维数组线性DP
一维:长度
二维:奇数的个数
三维:偶数的个数
四维:奇偶性

附上代码

#include<bits/stdc++.h>
using namespace std;
#define ll long long
const int INF=0x3f3f3f;
const int N=105;
int f[N][N][N][2];
int a[N],sum[N];
int main(){
	ios::sync_with_stdio(0);
	cin.tie(0);cout.tie(0);
	
	int n;
	cin>>n; 
	int odd=n-n/2,even=n/2;
	for(int i=1;i<=n;i++){
		cin>>a[i];
		if(a[i]){
			if(a[i]&1) odd--;
			else even--;
		}
		else
			sum[i]++;
	}
	memset(f,INF,sizeof f);
	for(int i=1;i<=n;i++)
		sum[i]+=sum[i-1];
	if(a[1]){
		if(a[1]&1) f[1][0][0][1]=0;
		else f[1][0][0][0]=0;
	}
	else{
		f[1][1][0][1]=0;
		f[1][0][1][0]=0;
	}
	for(int i=2;i<=n;i++){
		for(int j=0;j<=odd;j++){
			int k=sum[i]-j;
			if(k>sum[i]||j>sum[i]||k<0)
				continue;
			else{
				if(a[i]){
					if(a[i]&1)
						f[i][j][k][1]=min(f[i-1][j][k][0]+1,f[i-1][j][k][1]);
					else
						f[i][j][k][0]=min(f[i-1][j][k][1]+1,f[i-1][j][k][0]);
				}
				else{
					if(j) f[i][j][k][1]=min(f[i-1][j-1][k][0]+1,f[i-1][j-1][k][1]);
					if(k) f[i][j][k][0]=min(f[i-1][j][k-1][1]+1,f[i-1][j][k-1][0]);
				}
			}
		}
	}
	int ans=0;
	if(a[n]){
		if(a[n]&1)
			ans=f[n][odd][even][1];
		else
			ans=f[n][odd][even][0];
	}
	else
		ans=min(f[n][odd][even][0],f[n][odd][even][1]);
	cout<<ans<<endl;
	return 0;
}
发布了23 篇原创文章 · 获赞 5 · 访问量 1万+

猜你喜欢

转载自blog.csdn.net/Fiveneves/article/details/104129643