树网的核 AC代码交的,但是在这里全WA。用的 Θ(n) 的尺取法,样例和讨论区的 Hank 都过了。
特请各位大佬指教,感激不尽。
#include <cstdio>
#include <vector>
using namespace std;
struct Node
{
int to,w;
};
int n,m,total=1,ans=1e9,mark[2],deep[300005],pred[300005],path[300005][2];
bool flag[300005];
vector<Node> node[300005];
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^48);
ch=getchar();
}
return x*f;
}
inline void dfs(int father,int u,int t)
{
for(register int r=0;r<node[u].size();++r)
if(node[u][r].to!=father)
{
int v=node[u][r].to,w=node[u][r].w;
deep[v]=deep[u]+w;
if(t==1) path[v][0]=u,path[v][1]=w;
dfs(u,v,t);
}
if(deep[u]>deep[mark[t]]) mark[t]=u;
}
inline int get_len(int father,int u,int dis)
{
for(register int r=0;r<node[u].size();++r)
if(node[u][r].to!=father) return get_len(u,node[u][r].to,dis+node[u][r].w);
return dis;
}
int main()
{
n=read(),m=read();
for(register int i=1,u,v,w;i<n;++i)
u=read(),v=read(),w=read(),node[u].push_back(Node{v,w}),node[v].push_back(Node{u,w});
dfs(0,1,0),deep[mark[0]]=0,dfs(0,mark[0],1);
for(register int u=mark[1];u&&u!=mark[0];u=path[u][0]) total++,pred[total]=pred[total-1]+path[u][1];
for(register int l=1,r=1;r<=total;++r)
{
while(l<=r&&pred[r]-pred[l-1]>m) l++;
ans=min(ans,max(pred[l-1],pred[total]-pred[r]));
}
if(!ans)
{
for(register int u=mark[1];u;u=path[u][0]) flag[u]=true;
for(register int u=mark[1];u;u=path[u][0])
for(int r=0;r<node[u].size();++r)
{
int v=node[u][r].to,w=node[u][r].w;
if(!flag[v]) ans=max(ans,get_len(u,v,w));
}
}
return printf("%d",ans),0;
}