78 lines
1.9 KiB
C++
78 lines
1.9 KiB
C++
#include <algorithm>
|
|
#include <cstdio>
|
|
#include <cstring>
|
|
using namespace std;
|
|
typedef long long LL;
|
|
const int kMaxn = 1e5 + 10;
|
|
const LL kInf = 1e18;
|
|
LL f[kMaxn];
|
|
int n, w[kMaxn];
|
|
struct Data {
|
|
int x, oid;
|
|
LL y;
|
|
} val[kMaxn], tmp[kMaxn];
|
|
double Slope(int a, int b) {
|
|
if (val[a].x == val[b].x) {
|
|
return val[a].y < val[b].y ? kInf : -kInf;
|
|
}
|
|
return double(val[b].y - val[a].y) / double(val[b].x - val[a].x);
|
|
}
|
|
void CDQ(int L, int R) {
|
|
if (L == R) {
|
|
val[L].y = f[val[L].oid] + val[L].x * (LL)val[L].x;
|
|
// printf("y(%d)=%d\n",L,val[L].y);
|
|
return;
|
|
}
|
|
int M = (L + R) >> 1;
|
|
for (int i = L, pl = L, pr = M + 1; i <= R; i++) {
|
|
if (val[i].oid <= M) {
|
|
tmp[pl++] = val[i];
|
|
} else {
|
|
tmp[pr++] = val[i];
|
|
}
|
|
}
|
|
for (int i = L; i <= R; i++) val[i] = tmp[i];
|
|
CDQ(L, M);
|
|
int *Q = new int[R - L + 100](), QL = 1, QR = 0;
|
|
for (int i = L; i <= M; i++) {
|
|
while (QL < QR && Slope(Q[QR - 1], Q[QR]) > Slope(Q[QR], i))
|
|
QR--;
|
|
Q[++QR] = i;
|
|
}
|
|
for (int i = M + 1; i <= R; i++) {
|
|
while (QL < QR && Slope(Q[QL], Q[QL + 1]) < 2 * val[i].x) QL++;
|
|
int x = val[i].oid, y = val[Q[QL]].oid;
|
|
f[x] = min(f[x], f[y] - w[x] +
|
|
(val[i].x - val[Q[QL]].x) * (LL)(val[i].x - val[Q[QL]].x));
|
|
}
|
|
CDQ(M + 1, R);
|
|
for (int i = L, pl = L, pr = M + 1; i <= R; i++) {
|
|
if (pr > R || (pl <= M && val[pl].x < val[pr].x))
|
|
tmp[i] = val[pl++];
|
|
else
|
|
tmp[i] = val[pr++];
|
|
}
|
|
for (int i = L; i <= R; i++) val[i] = tmp[i];
|
|
delete[] Q;
|
|
}
|
|
int main() {
|
|
#ifdef local
|
|
freopen("pro.in", "r", stdin);
|
|
#endif
|
|
scanf("%d", &n);
|
|
for (int i = 1; i <= n; i++) {
|
|
scanf("%d", &val[i].x);
|
|
val[i].oid = i;
|
|
f[i] = kInf * 4;
|
|
}
|
|
f[1] = 0;
|
|
for (int i = 1; i <= n; i++) {
|
|
scanf("%d", &w[i]);
|
|
if (i >= 2) f[1] += w[i];
|
|
}
|
|
sort(val + 1, val + 1 + n,
|
|
[](const Data &a, const Data &b) { return a.x < b.x; });
|
|
CDQ(1, n);
|
|
printf("%lld\n", f[n]);
|
|
return 0;
|
|
} |