# | Time | Username | Problem | Language | Result | Execution time | Memory |
---|---|---|---|---|---|---|---|
883548 | nghiaaa | Harbingers (CEOI09_harbingers) | C++14 | 120 ms | 37904 KiB |
This submission is migrated from previous version of oj.uz, which used different machine for grading. This submission may have different result if resubmitted.
#include <bits/stdc++.h>
using namespace std;
#define ll long long
#define db double
#define ii pair<int,int>
#define f first
#define s second
#define mp make_pair
#define mt make_tuple
#define pb push_back
#define all(v) v.begin(),v.end()
#define BIT(i) ((ll)1<<(i))
#define endl "\n"
#define debug(x) for (auto p: x) cout<<p<<' ';cout<<endl
#define forw(i,j,z) for(int i=(int)j;i<=(int)z;i++)
#define forw2(i,j,z,k) for(int i=(int)j;i<=(int)z;i+=k)
#define ford(i,j,z) for (int i=(int)j;i>=(int)z;i--)
#define ford2(i,j,z,k) for (int i=(int)j;i>=(int)z;i-=k)
#define sz(a) (int)a.size()
const int N=1e5;
const ll inf=LLONG_MAX;
const int smallinf=1e9+1;
struct Line{
ll a,b;
Line(){}
Line(ll a1,ll b1):a(a1),b(b1){}
ll operator ()(const ll x) const{
return a*x+b;
}
};
int timeDFS=0,n,prepare[N+1],velocity[N+1];
vector<ii> adj[N+1];
ll dp[N+1],h[N+1];
struct seg{
int id=1;
seg *L=NULL,*R=NULL;
}; seg *BIGTREE=new seg;
vector<pair<bool,int> > changes[N+1];
vector<Line> origin(N+1);
void update(int u,int l=1,int r=smallinf,seg *tree=BIGTREE,bool ready=false)
{
if (u==1||(ready&&tree->id==1)) return ;
if (l+1==r){
if (origin[tree->id](l) > origin[u](l))
tree->id=u;
}
else{
int mid=(l+r)>>1;
if (origin[tree->id].a>origin[u].a){
swap(tree->id,u);
}
if (origin[tree->id](mid)<origin[u](mid))
{
if (tree->L==NULL) tree->L=new seg;
changes[timeDFS].push_back(mp(0,tree->L->id));
update(u,l,mid,tree->L);
}
else{
swap(tree->id,u);
if (tree->R==NULL) tree->R=new seg;
changes[timeDFS].push_back(mp(1,tree->R->id));
update(u,mid,r,tree->R,1);
}
}
}
ll query(ll x,int l=1,int r=smallinf,seg *tree=BIGTREE)
{
if (tree==NULL) return origin[1](x);
if (l+1==r) return origin[tree->id](x);
int mid=(l+r)>>1;
if (x<mid) return min(origin[tree->id](x),query(x,l,mid,tree->L));
else return min(origin[tree->id](x),query(x,mid,r,tree->R));
}
void dfs(int u,int dad)
{
int now=++timeDFS;
if (u>1){
dp[u]=query(velocity[u])+h[u]*velocity[u]+prepare[u];
origin[now]=Line(-h[u],dp[u]);
changes[now].push_back(mp(0,BIGTREE->id));
update(now);
}
forw(i,0,sz(adj[u])-1) if (adj[u][i].f!=dad)
{
int v=adj[u][i].f,d=adj[u][i].s;
h[v]=h[u]+d;
dfs(v,u);
}
if (u>1){
seg *tree=BIGTREE;
tree->id=changes[now][0].s;
forw(i,1,sz(changes[now])-1)
{
if (!changes[now][i].f) tree=tree->L;
else tree=tree->R;
tree->id=changes[now][i].s;
}
changes[now].clear();
}
}
void solve()
{
origin[1]=Line(0,0);
update(1,smallinf,1);
cin>>n;
forw(i,2,n)
{
int u,v,d;
cin>>u>>v>>d;
adj[u].push_back(mp(v,d));
adj[v].push_back(mp(u,d));
}
forw(i,2,n) cin>>prepare[i]>>velocity[i];
dfs(1,1);
forw(i,2,n) cout<<dp[i]<<' ';
}
signed main()
{
ios_base::sync_with_stdio(false);
cin.tie(0);
//cout<<setprecision(6)<<fixed;
//time_t TIME_TU=clock();
int t=1;
//cin>>t;
while(t--)
solve();
//time_t TIME_TV=clock();
//cerr<<(db)(TIME_TV-TIME_TU)/CLOCKS_PER_SEC<<endl;
return 0;
}
# | Verdict | Execution time | Memory | Grader output |
---|---|---|---|---|
Fetching results... |