思路是按照排序结果的不同将值域划成 O(m2) 段,每段跑一段最小生成树,然后扫描线统计答案。
但是一直 WA on test 8
。
#include<bits/stdc++.h>
using namespace std;
#define rg register
#define ll long long
#define ull unsigned ll
#define inf 0x3f3f3f3f
#define lowbit(x) (x&(-x))
#define eps 1e-8
const double alpha=0.73;
const int djq=1e9+9;
inline void file(){
freopen("P5050_1.in","r",stdin);
freopen("P5050_1.ans","w",stdout);
}
char buf[1<<21],*p1=buf,*p2=buf;
inline int getc(){
return p1==p2&&(p2=(p1=buf)+fread(buf,1,1<<21,stdin),p1==p2)?EOF:*p1++;
}
inline int read(){
rg int ret=0,f=0;char ch=getc();
while(!isdigit(ch)){if(ch==EOF)exit(0);if(ch=='-')f=1;ch=getc();}
while(isdigit(ch)){ret=ret*10+ch-48;ch=getc();}
return f?-ret:ret;
}
//inline int ksm(int base,int p){ int ret=1; while(p){ if(p&1) ret=1ll*ret*base%djq; base=1ll*base*base%djq,p>>=1; } return ret; }
int n,m,p,k,a,b,c;
struct edge{
int u,v,w,rw,id;
edge(int u=0,int v=0,int w=0,int rw=0,int id=0):u(u),v(v),w(w),rw(rw),id(id) {}
bool operator<(const edge& t)const{
return rw^t.rw?rw<t.rw:id<t.id;
}
}e[305];
struct pa{
int v;
bool operator<(const pa& t)const{
return v^t.v?v<t.v:1;
}
}q[10000005];
map<int,bool> mp;
bool vis[305];
ll ans;
int f[55];
int find(int x){
if(f[x]==x) return x;
return f[x]=find(f[x]);
}
signed main(){
//file();
n=read(),m=read();
for(rg int i=1,u,v,w;i<=m;++i) u=read(),v=read(),w=read(),e[i]=edge(u,v,w,w,i);
sort(e+1,e+1+m);
for(rg int i=1;i<=m;++i){
for(rg int j=1;j<i;++j){
const int mid=(e[i].w+e[j].w)/2;
mp[mid]=1;
}
}
p=read(),k=read(),a=read(),b=read(),c=read();
for(rg int i=1;i<=p;++i) q[i].v=read();
for(rg int i=p+1;i<=k;++i) q[i].v=(1ll*q[i-1].v*a+b)%c;
sort(q+1,q+1+k); int j=1;
//for(rg int i=1;i<=k;++i) printf("%d ",q[i].v);
//puts("");
mp[c]=1;
for(map<int,bool>::iterator i=mp.begin();i!=mp.end();++i){
const int x=((*i).first);
for(rg int j=1;j<=n;++j) f[j]=j;
memset(vis,0,sizeof(vis));
for(rg int i=1;i<=m;++i) e[i].rw=abs(e[i].w-x);
sort(e+1,e+1+m); ll pre=0,nex=0,cpre=0,cnex=0;
for(rg int i=1;i<=m;++i){
const int fx=find(e[i].u),fy=find(e[i].v);
if(fx==fy) continue;
f[fx]=fy; vis[e[i].id]=1; nex+=e[i].w; ++cnex;
if(cnex==n-1) break;
}
for(rg int i=1;i<=m;++i) e[i].rw=e[i].w;
sort(e+1,e+1+m); int g=1;
while(q[j].v<=x&&j<=k){
while(e[g].w<=q[j].v&&g<=m){
if(vis[e[g].id]) nex-=e[g].w,pre+=e[g].w,--cnex,++cpre;
++g;
}
const ll nans=1ll*q[j].v*cpre-pre+nex-1ll*q[j].v*cnex;
//printf("%lld %lld %lld %d %d\n",nans,cpre,cnex,q[j].v,x);
ans^=nans; ++j;
}
}
printf("%lld",ans);
return 0;
}
/*
*/