分析
时间复杂度
状态数量 * 状态转移
$O(N^2 * N) ==> O(N^3)$
c++代码
#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
const int N = 110, inf = 0x3f3f3f3f;
char s[N];
int f[N][N]; // f[i][j]代表将i~j个字符变成GBE的所有方案的集合的最小值
bool check(int a, int b)
{
if (s[a] == '[' && s[b] == ']' || s[a] == '(' && s[b] ==')') return true;
return false;
}
int main()
{
scanf("%s", s + 1);
int n = strlen(s + 1);
for (int len = 1; len <= n; len++)
for (int l = 1; l + len - 1 <= n; l++)
{
int r = l + len - 1;
if (len == 1) f[l][r] = 1;
else
{
f[l][r] = inf;
if (check(l, r)) f[l][r] = min(f[l][r], f[l + 1][r - 1]);
for (int k = l; k <= r; k++)
f[l][r] = min(f[l][r], f[l][k] + f[k + 1][r]);
}
}
cout << f[1][n] << endl;
return 0;
}
你的k都越界了,当k等于r的时候
他这个是从s+1开始读的数据啊,我看了好多题解,很多都越界了,包括y总写的,我自己写的都出现了f[0][-1]这种东西,巧的是我还能对这种玩意进行赋值,只有答主这种写法是最优解
这个跟从s+1开始读没关系的,你看当k等于r的时候 f[l][r]=min(f[l][r],f[l][r]+f[r+1][r]) 他的代码能过是因为f[r+1][r]是全局数组,值是0所以不影响, 应该改成 for (int k = l; k < r; k++)
听君一席话,胜读半月书,我订阅你了
能不能换成是 求这个串里面 最大的合法子序列长度 然后再用总长度减去这个最长合法序列的长度 就是答案。
你写出来了吗,xd,分析最长合法子序列还是要和y总一样的dp
可以的 这一个就是用这个做法https://www.acwing.com/solution/content/8845/
%%%
xd,你发现没,他的dp分析和y总一样
其实他跟y总的分析思路是不一样的,y总是直接就问题去解的,但小呆呆那个是用总长度减去最长合法序列的长度,也就相当于把现在这个问题转化为目标字符串中拥有的最长合法子序列的问题 两种分析出发点不一样
你仔细看看dp转移的过程,你会发现求最长序列的时候会直接求出答案。
Orz
可不可以使用栈来进行处理呢?
应该不行。
我试了,怎么都不行