Garsia–Wachs算法解决石子合并
前排提示:本文并非题解,仅放在题解夹里,若想了解Garsia–Wachs算法原理请跳转:oi_wiki
关于题库有道四边形不等式的题但是无法通过四边形不等式解决
- 我们先写\(n^2\)
#include<bits/stdc++.h>
#define endl '\n'
using namespace std;
constexpr int maxn=2e4+10;
int n;
int s[maxn],f[maxn][maxn],p[maxn][maxn];
void init() {for (int i=1;i<=n;i++) p[i][i]=i;}
int main()
{
cin >> n;
for (int i=1;i<=n;i++)
{
cin >> s[i];
s[i]+=s[i-1];
}
init();
for (int l=2;l<=n;l++)
{
for (int i=1;i<=n-l+1;i++)
{
int j=i+l-1;
f[i][j]=0x7fffffff;
for (int k=p[i][j-1];k<=p[i+1][j];k++)
{
int x=f[i][k]+f[k+1][j]+s[j]-s[i-1];
if (f[i][j]>=x)
{
f[i][j]=x;
p[i][j]=k;
}
}
}
}
cout << f[1][n] << endl;
return 0;
}
包炸- 介绍新算法的结论
我不会告诉你我只知道结论的
有一个数组
a[](0 ~ n-1),每次查找最小的k使满足a[k-1]<=a[k+1],将a[k],a[k-1]合并,设和为temp,后k向前找第一个位置设为c满足a[c]>temp,将temp插在c后,每次累加结果,就可以诡异の解决
- 给出清晰不压行707B运行888KB代码
#include<bits/stdc++.h>
#define endl '\n'
using namespace std;
constexpr int maxn=1e5+10;
inline int read() {int x=0,f=1;char ch=getchar();while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}while(ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+(ch-'0');ch=getchar();}return x*f;}
int n,ans;
vector<int> l;
int get()
{
int k=l.size()-2;
for (int i=0;i<l.size()-2;i++) if (l[i]<=l[i+2]) {k=i;break;}
int temp=l[k]+l[k+1];
l.erase(l.begin()+k),l.erase(l.begin()+k);
int c=-1;
for (int i=k-1;i>=0;i--) if (l[i]>temp) {c=i;break;}
l.insert(l.begin()+c+1,temp);
return temp;
}
int main()
{
n=read();
for (int i=1;i<=n;i++) l.push_back(read());
for (int i=0;i<n-1;i++) ans+=get();
cout << ans << endl;
return 0;
}

浙公网安备 33010602011771号