【题解】【AcWing】3505. 最长ZigZag子序列

288 阅读1分钟

本文已参与「新人创作礼」活动,一起开启掘金创作之路。

3505. 最长ZigZag子序列

原题传送:AcWing 3505. 最长ZigZag子序列

一个整数序列的子序列是指从给定序列中随意地(不一定连续)去掉若干个整数(可能一个也不去掉)后所形成的整数序列。

对于一个整数序列 x1,x2,,xnx_1,x_2,…,x_n ,如果满足下列两个条件之一:

  1. i[1,n1]\forall i \in [1,n-1] ,当 i%2==1i\%2==1 时, xixi+1x_i-x_{i+1} 为正,当 i%2==0i\%2==0 时, xixi+1x_i-x_{i+1} 为负。
  2. i[1,n1]\forall i \in[1,n-1] ,当 i%2==1i\%2==1 时, xixi+1x_i-x_{i+1} 为负,当 i%2==0i\%2==0 时, xixi+1x_i-x_{i+1} 为正。

那么,我们就称这个整数序列为ZigZag序列。

换句话说,ZigZag序列就是一个序列内元素在增大和减小之间不断切换的序列。

例如 1,7,4,9,2,51,7,4,9,2,5 就是一个ZigZag序列。

现在,给定一个长度为 nn 的整数序列,请你求出它的最长ZigZag子序列的长度。

输入格式

第一行包含整数 nn

第二行包含 nn 个整数。

输出格式

输出一个整数,表示最长ZigZag子序列的长度。

数据范围

1n501 \le n \le 50 , 序列内元素取值范围 [1,1000][1,1000]

输入样例:

6
1 7 4 9 2 5

输出样例:

6

思路:

f[i]以第i个数结尾且前一个数比第i个数大的方案数,g[i]以第i个数结尾且前一个数比第i个数小的方案数;两者的最大值即为答案。

题解:

#include <bits/stdc++.h>

using namespace std;

const int N = 55;

int n;
int w[N];
int f[N], g[N];

int main()
{
	cin >> n;
	
	for(int i = 0; i < n; i++)
		cin >> w[i];
		
	int res = 0;
	for(int i = 0; i < n; i++)
	{
		f[i] = g[i] = 1;
		for(int j = 0; j < i; j++)
			if(w[j] > w[i]) f[i] = max(f[i], g[j] + 1);
			else if(w[j] < w[i]) g[i] = max(g[i], f[j] + 1);
		res = max(f[i], g[i]); 
	}
	cout << res << endl;
	
	return 0;
}