调了1d了 无果 求调
查看原帖
调了1d了 无果 求调
401393
一只绝帆楼主2023/2/26 21:08
// Problem: P4069 [SDOI2016]游戏
// Contest: Luogu
// URL: https://www.luogu.com.cn/problem/P4069
// Memory Limit: 250 MB
// Time Limit: 1000 ms

#include<bits/stdc++.h>
#define y1 y_1
#define l(x) (x<<1)
#define r(x) (x<<1|1)
#define mid ((L+R)>>1)
typedef long long ll;
using namespace std;
#define getchar() (p1==p2&&(p2=(p1=buf)+fread(buf,1,1<<21,stdin),p1==p2)?EOF:*p1++)
char *p1,*p2,buf[1<<21];
ll read()
{
	ll s=0,w=0;char ch=getchar();
	while(ch<'0'||ch>'9') w|=(ch=='-'),ch=getchar();
	while(ch>='0'&&ch<='9') s=(s<<3)+(s<<1)+(ch^48),ch=getchar();
	return w?-s:s;
}
const int N=2e5+5,M=4e5+5;
const ll inf=123456789123456789ll;
int n,m,qnt,c[N<<2];
int cnt,u[M],v[M],start[M],Next[M],fa[N],top[N],siz[N],dep[N],tot,dfn[N],dfx[N],son[N];
ll w[M],dis[N],mi[N<<2];
struct LINE{
	ll k,b;
	ll operator()(ll x) {return k*dis[dfx[x]]+b;}
} li[N];
int l,r;
void pushup(int L,int R,int d)
{
	mi[d]=min(min(mi[l(d)],mi[r(d)]),c[d]?min(li[c[d]](L),li[c[d]](R)):inf);
}
void modify(int id,int L,int R,int d)
{
	int x=id,&y=c[d];
	if(r<L||R<l) return;
	if(l<=L&&R<=r)
	{
		if(!y) return y=x,pushup(L,R,d);if(li[x](mid)<li[y](mid)) swap(x,y);
		if(L==R) return pushup(L,R,d);
		if(li[x](L)<li[y](L)) modify(x,L,mid,l(d));
		if(li[x](R)<li[y](R)) modify(x,mid+1,R,r(d));
		return pushup(L,R,d);
	}
	modify(id,L,mid,l(d));modify(id,mid+1,R,r(d));
	pushup(L,R,d);
}
int ans;
ll query(int L,int R,int d)
{
	if(l<=L&&R<=r) return mi[d];
	if(R<l||r<L) return inf;
	return min(c[d]?min(li[c[d]](max(l,L)),li[c[d]](min(r,R))):inf,
			min(query(L,mid,l(d)),query(mid+1,R,r(d))));
}
void add(int x,int y,ll z)
{
	u[++cnt]=x;v[cnt]=y;w[cnt]=z;Next[cnt]=start[x];start[x]=cnt;
}
void dfs1(int x)
{
	dep[x]=dep[fa[x]]+1;
	siz[x]=1;
	for(int i=start[x];i;i=Next[i])
	{
		if(v[i]==fa[x]) continue;fa[v[i]]=x;
		dis[v[i]]=dis[x]+w[i];
		dfs1(v[i]);
		siz[x]+=siz[v[i]];
		if(siz[v[i]]>siz[son[x]]) son[x]=v[i];
	}
}
void dfs2(int x,int tp)
{
	dfn[x]=++tot;dfx[tot]=x;top[x]=tp;
	if(son[x]) dfs2(son[x],tp);
	for(int i=start[x];i;i=Next[i])
	{
		if(v[i]==fa[x]||v[i]==son[x]) continue;
		dfs2(v[i],v[i]);
	}
}
int lca(int x,int y)
{
	while(top[x]!=top[y])
	{
		if(dep[x]<dep[y]) swap(x,y);
		x=fa[top[x]];
	}
	return dep[x]<dep[y]?x:y;
}
void modify(int x,int f,int id)
{
	while(top[x]!=top[f]) l=dfn[top[x]],r=dfn[x],modify(id,1,n,1),x=fa[top[x]];
	l=dfn[f],r=dfn[x],modify(id,1,n,1);
}
ll query(int x,int y)
{
	ll ans=inf;
	while(top[x]!=top[y])
	{
		if(dep[top[x]]<dep[top[y]]) swap(x,y);
		l=dfn[top[x]],r=dfn[x];
		ans=min(ans,query(1,n,1));
		x=fa[top[x]];
	}
	if(dep[x]>dep[y]) swap(x,y);
	l=dfn[x];r=dfn[y];
	return min(ans,query(1,n,1));
}
int main()
{
	memset(mi,0x3f,sizeof mi);
	n=read();m=read();
	for(int i=1,x,y,z;i<=n-1;i++) x=read(),y=read(),z=read(),add(x,y,z),add(y,x,z);
	dfs1(1);dfs2(1,1);
	for(ll s,t,a,b,l;m--;)
	{
		if(read()==1)
		{
			s=read(),t=read(),a=read(),b=read();l=lca(s,t);
			li[++qnt]={-a,a*dis[s]+b};modify(s,l,qnt);
			li[++qnt]={a,a*(dis[s]-2*dis[l])+b};modify(t,l,qnt);
		}
		else
		{
			s=read(),t=read();
			cout<<query(s,t)<<endl;
		}
	}
	return 0;
}
2023/2/26 21:08
加载中...