就爆零了
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
#define int long long
const int N=1e5+10;
const int INF=0x3f3f3f3f3f3f3f3f;
int n,k;
int dis[N],c[N],s[N],w[N],dp[N];
int End[N],Start[N];
//图
struct Edge{
int to;
int nxt;
}edge[N<<2];
int head[N],tot=-1;
void init(){
memset(head,-1,sizeof(head));
tot=-1;
}
void add(int x,int y){
edge[++tot].to=y;
edge[tot].nxt=head[x];
head[x]=tot;
}
//线段树
struct Tree{
int left;
int right;
int minn;
int lazy;
}tree[N<<2];
#define L(root) tree[root].left
#define R(root) tree[root].right
#define M(root) tree[root].minn
#define T(root) tree[root].lazy
#define lson root<<1
#define rson root<<1|1
void pushup(int root){
M(root)=min(M(lson),M(rson));
}
void pushdown(int root){
if(T(root)!=0){
M(lson)+=T(root);
M(rson)+=T(root);
T(lson)+=T(root);
T(rson)+=T(root);
T(root)=0;
}
}
void build(int root,int l,int r){
L(root)=l;
R(root)=r;
T(root)=0;
if(l==r){
M(root)=dp[l];
return ;
}
int mid=(l+r)>>1;
build(lson,l,mid);
build(rson,mid+1,r);
pushup(root);
}
void update(int root,int l,int r,int tmp){
if(l>r)
return;
if(l<=L(root)&&r>=R(root)){
M(root)+=tmp;
T(root)+=tmp;
return;
}
pushdown(root);
int mid=(L(root)+R(root))>>1;
if(l<=mid)
update(lson,l,r,k);
if(r>mid)
update(rson,l,r,k);
pushup(root);
}
int query(int root,int l,int r){
if(l>r)
return 0;
if(l<=L(root)&&r>=R(root)){
return M(root);
}
pushdown(root);
int mid=(L(root)+R(root))>>1;
int ans=INF;
if(l<=mid)
ans=min(ans,query(lson,l,r));
if(r>mid)
ans=min(ans,query(rson,l,r));
return ans;
}
signed main(){
ios::sync_with_stdio(false);
cin.tie(0);
cout.tie(0);
init();
cin>>n>>k;
for(int i=2;i<=n;i++)
cin>>dis[i];
for(int i=1;i<=n;i++)
cin>>c[i]; //val
for(int i=1;i<=n;i++)
cin>>s[i]; //range
for(int i=1;i<=n;i++)
cin>>w[i]; //pay
++n;
++k;
dis[n]=w[n]=INF;
for(int i=1;i<=n;i++){
Start[i]=lower_bound(dis+1,dis+1+n,dis[i]-s[i])-dis;
End[i]=lower_bound(dis+1,dis+1+n,dis[i]+s[i])-dis;
if(dis[End[i]]>dis[i]+s[i])
End[i]--;
add(End[i],i);
}
int now=0;
for(int i=1;i<=n;i++){
dp[i]=now+c[i];
for(int j=head[i];~j;j=edge[j].nxt){
int v=edge[j].to;
now+=w[v];
}
}
int ans=dp[n];
for(int i=2;i<=k;i++){
build(1,1,n);
for(int j=1;j<=n;j++){
dp[j]=query(1,1,j-1)+c[j];
for(int p=head[j];~p;p=edge[p].nxt){
int v=edge[p].to;
update(1,1,Start[v]-1,w[v]);
}
}
ans=min(ans,dp[n]);
}
cout<<ans;
return 0;
}