#include #include #include #include using namespace std; int hhy=0; struct nd{ nd * c[2]; nd * p; long long sm,lzy,pt,slp; long long lzy_pt; long long inc,prv; long long sm_inc; long long sm_len; bool rev; nd(nd * pa,long long pp,long long s,long long pv){ c[0]=c[1]=NULL; prv=pv; p=pa; sm=1; lzy_pt=0; rev=false; lzy=0; pt=pp; slp=s; sm_len=pp-prv; inc=(pp-prv) * slp; sm_inc=inc; } }; struct splay{ nd * root; splay(){ root=NULL; } long long num(nd * t){ if(t==NULL)return 0; return t->sm; } long long leng(nd * t){ if(t==NULL)return 0; return t->sm_len; } long long incc(nd * t){ if(t==NULL)return 0; return t->sm_inc; } long long ty(nd * t){ if(t->p==NULL)return -1; if(t->p->c[0]==t)return 0; return 1; } void push_down(nd * t){ if(t->rev){ swap(t->c[0],t->c[1]); if(t->c[0]!=NULL){ t->c[0]->rev = ! t->c[0]->rev; } if(t->c[1]!=NULL){ t->c[1]->rev = ! t->c[1]->rev; } t->rev=false; } if(t->lzy){ t->slp+=t->lzy; t->inc+=t->lzy * (t->pt-t->prv); t->sm_inc+=t->lzy * t->sm_len; if(t->c[0]!=NULL){ t->c[0]->lzy += t->lzy; } if(t->c[1]!=NULL){ t->c[1]->lzy += t->lzy; } t->lzy=0; } if(t->lzy_pt){ if(t->pt!= 1ll<<60){ t->pt+=t->lzy_pt; } if(t->prv!= -1ll<<60){ t->prv+=t->lzy_pt; } if(t->c[0]!=NULL){ t->c[0]->lzy_pt += t->lzy_pt; } if(t->c[1]!=NULL){ t->c[1]->lzy_pt += t->lzy_pt; } t->lzy_pt=0; } } void fix(nd * t){ push_down(t); if(t->c[0]!=NULL){ push_down(t->c[0]); } if(t->c[1]!=NULL){ push_down(t->c[1]); } t->inc = (t->pt-t->prv) * t->slp; t->sm= num(t->c[0])+num(t->c[1])+1; t->sm_len= leng(t->c[0])+leng(t->c[1])+(t->pt-t->prv); t->sm_inc= incc(t->c[0])+incc(t->c[1])+t->inc; } void rotate(nd * t){ long long c=ty(t); if(c==-1)return; nd * p = t->p; if(p==NULL)return; if(p->p!=NULL){ p->p->c[ty(p)]=t; } t->p=p->p; p->p=t; p->c[c]=t->c[1-c]; if(t->c[1-c]!=NULL){ t->c[1-c]->p=p; } t->c[1-c]=p; fix(p); fix(t); if(t->p!=NULL){ fix(t->p); } } nd * sp(nd * t){ while(t->p!=NULL){ if(t->p->p==NULL){ rotate(t); continue; } if(ty(t) == ty(t->p)){ rotate(t->p); rotate(t); } else { rotate(t); rotate(t); } } return t; } void _print(nd * t,long long pt,long long slp){ if(t==NULL)return; pt+= t->lzy_pt; slp += t->lzy; _print(t->c[0],pt,slp); cout<pt + pt <<" "<slp + slp<<" "<prv<c[1],pt,slp); } void print(){ return; cout<<"======"<slp slp >= slo){ if(t->c[0]==NULL){ break; } else { t=t->c[0]; } } else { if(t->c[1]==NULL){ break; } else { t=t->c[1]; } } } push_down(t); root=sp(t); return bst->pt; } nd * lookuppt(nd * t,long long pt,bool is_not_root=false){ nd * bst=NULL; while(true){ push_down(t); if(t->pt <=pt){ bst=t; } if(pt < t->pt){ if(t->c[0]==NULL){ break; } else { t=t->c[0]; } } else { if(t->c[1]==NULL){ break; } else { t=t->c[1]; } } } push_down(t); if(!is_not_root){ root=sp(t); } else { sp(t); } return bst; } nd * lookuppt2(nd * t,long long pt,bool is_not_root=false){ nd * bst=NULL; while(true){ push_down(t); if(pt <= t->pt ){ bst=t; } if(pt <= t->pt){ if(t->c[0]==NULL){ break; } else { t=t->c[0]; } } else { if(t->c[1]==NULL){ break; } else { t=t->c[1]; } } } push_down(t); if(!is_not_root){ root=sp(t); } else { sp(t); } return bst; } pair get_lookuppt2(long long x){ nd * t=lookuppt2(root,x); return make_pair(t->pt,t->slp); } pair get_lookuppt(long long x){ nd * t=lookuppt(root,x); return make_pair(t->pt,t->slp); } void split1(nd * t,long long pt,bool is_after,nd * &l ,nd * &r){ if(is_after){ t=sp(lookuppt(t,pt)); r=t->c[1]; if(r!=NULL) r->p=NULL; t->c[1]=NULL; fix(t); l=t; } else { t=sp(lookuppt(t,pt)); l=t->c[0]; if(l!=NULL) l->p=NULL; t->c[0]=NULL; fix(t); r=t; } } void split2(nd * t,long long pt,bool is_after,nd * &l ,nd * &r){ if(is_after){ t=sp(lookuppt2(t,pt)); r=t->c[1]; if(r!=NULL) r->p=NULL; t->c[1]=NULL; fix(t); l=t; } else { t=sp(lookuppt2(t,pt)); l=t->c[0]; if(l!=NULL) l->p=NULL; t->c[0]=NULL; fix(t); r=t; } } void split_upd(nd * t,long long l,long long r,bool is_after,bool is_after2,nd * &left,nd * &mid,nd * &right){ split2(t,r,is_after2,mid,right); split2(mid,l,is_after,left,mid); } void split_query(nd * t,long long l,long long r,bool is_after,bool is_after2,nd * &left,nd * &mid,nd * &right){ split1(t,r,is_after2,mid,right); split2(mid,l,is_after,left,mid); } nd * _leftmost(nd * t){ while(t->c[0]){ push_down(t); t=t->c[0]; } push_down(t); t=sp(t); return t; } long long leftmost(){ nd * t=root; while(t->c[0]){ push_down(t); t=t->c[0]; } push_down(t); root=sp(t); return t->slp; } long long rightmost(){ nd * t=root; while(t->c[1]){ push_down(t); t=t->c[1]; } push_down(t); root=sp(t); return t->slp; } void initiate(){ root=new nd(NULL,0,-1ll<<60,-1ll<<60); root->c[1]=new nd(root,1ll<<60,1ll<<60,0); } void insert(long long pt){ root=sp(lookuppt2(root,pt)); if(root->pt==pt){ return; } hhy++; nd * l=root->c[0]; root->c[0]=new nd(root,pt,root->slp,root->prv); root->c[0]->c[0]=l; root->prv=pt; if(l!=NULL) l->p=root->c[0]; fix(root->c[0]); fix(root); } void insert_right(long long slp){ rightmost(); root->c[1]=new nd(root,1ll<<60,slp,root->pt); fix(root); } void insert_left(long long slp,long long pt){ leftmost(); root->c[0]=new nd(root,pt,slp,-1ll<<60); fix(root); } void erase_right(){ nd *left=root->c[0],*mid=root; //split_r(root,idx,idx, left,mid,right); delete mid; root=left; if(root!=NULL) root->p=NULL; } void erase_left(){ nd *right=root->c[1],*mid=root; //split_r(root,idx,idx, left,mid,right); delete mid; root=right; if(root!=NULL) root->p=NULL; } nd * join(nd * l,nd * r){ if(r==NULL)return l; r=_leftmost(r); r->c[0]=l; if(l!=NULL) l->p=r; fix(r); return r; } long long query(long long l,long long r,bool is_after){ nd *left,*mid,*right; split_query(root,l,r,is_after,is_after,left,mid,right); long long ret; if(mid==NULL){ ret=0; } else { ret=mid->sm_inc; } mid=join(left,mid); root=join(mid,right); return ret; } void upd(long long l,long long r,bool is_leftmost,long long add){ nd *left,*mid,*right; split_upd(root,l,r,!is_leftmost,true,left,mid,right); mid->lzy+=add; push_down(mid); mid=join(left,mid); root=join(mid,right); } }; struct func{ splay tree; long long yval; long long xval; }; struct ed{ long long ch; long long co; long long dx; long long ind; }; long long n; vector adj[200011]; func * dp[200011]; long long ll[200011]; long long rr[200011]; long long evaluate(func * &a,long long x){ if(x==a->xval){ return a->yval; } else if( xxval){ a->tree.print(); long long ans=-a->tree.query(x,a->xval,true) + a->yval; pair yy=a->tree.get_lookuppt2(x); ans+= (x-yy.first) * yy.second; return ans; } else { long long ans=a->tree.query(a->xval,x,true) + a->yval; pair yy=a->tree.get_lookuppt(x); pair yy2=a->tree.get_lookuppt2(x); ans+= (x-yy.first) * yy2.second; return ans; } } void cover(func * &a,long long co,long long dx,long long &l,long long &r){ l=-1ll<<60; r=1ll<<60; a->tree.print(); bool del=false; a->tree.root->lzy_pt+=co; a->xval+=co; a->tree.print(); while(true){ long long y=a->tree.rightmost(); if(y>=dx){ del=true; a->tree.erase_right(); } else { break; } } a->tree.print(); if(del){ a->tree.rightmost(); r=a->tree.root->pt; a->tree.insert_right(dx); } del=false; long long pot=-1ll<<60; while(true){ long long y=a->tree.leftmost(); if(y<=-dx){ del=true; pot=a->tree.root->pt; a->tree.erase_left(); } else { break; } } if(del){ l=pot; a->tree.insert_left(-dx,pot); } a->tree.print(); } void merge(func * &a, func * &b){ bool first=true; a->tree.print(); b->tree.print(); a->yval += evaluate(b,a->xval); long long last=-1; while(true){ if(b->tree.root==NULL)break; b->tree.leftmost(); a->tree.insert(b->tree.root->pt); a->tree.print(); if(first){ first=false; a->tree.upd(-1ll<<60,b->tree.root->pt,true,b->tree.root->slp); } else { a->tree.upd(last,b->tree.root->pt,false,b->tree.root->slp); } last=b->tree.root->pt; b->tree.erase_left(); } a->tree.print(); long long ot=a->tree.lookup(0); long long val=evaluate(a,ot); a->xval=ot; a->yval=val; } void dfs(long long nd,long long p){ bool has_val=false; long long id=-1,mx=-1; for(long long i=0;itree.root->sm){ mx=dp[ch]->tree.root->sm; id=ch; } } if(!has_val){ dp[nd]=new func(); dp[nd]->xval=0; dp[nd]->yval=0; dp[nd]->tree.initiate(); dp[nd]->tree.print(); return ; } dp[nd]=dp[id]; for(long long i=0;irr[ch]){ sol[ind]=curr_x-rr[ch]+co; dfs_get_edges(ch,nd,rr[ch]-co); } else if (curr_x < ll[ch]){ sol[ind]=curr_x-ll[ch]+co; dfs_get_edges(ch,nd,ll[ch]-co); } else { sol[ind]=co; dfs_get_edges(ch,nd,curr_x-co); } } } long long t; int main(){ //freopen("input05.txt","r",stdin); //freopen("otput05.txt","w",stdout); cin.sync_with_stdio(false); cin>>t; while(t--){ cin>>n; for(long long i=1;i<=n;i++){ adj[i].clear(); } for(long long i=0;i>a>>b>>c>>d; ed h; h.ch=b; h.co=c; h.dx=d; h.ind=i; adj[a].push_back(h); h.ch=a; adj[b].push_back(h); } dfs(1,1); cout<yval<<"\n"; dfs_get_edges(1,1,dp[1]->xval); for(int i=0;itree.root!=NULL){ dp[1]->tree.erase_left(); } } }