• [JSOI2017]原力


    题目大意:
      一个$n(nle5 imes10^4)$个点,$m(mle10^5)$条边的无向图。每条边有一个边权$w_i(w_ile10^6)$和一个附加属性$t_i(t_iin{R,G,B})$。定义一个三元环的价值为个条边权值之积,求所有满足每条边附加属性互不相同的三元环的价值和。

    思路:
      对结点按照度数分为两组分块,度数$gesqrt m$的算作重点,否则算轻点。对于三元环三个顶点都是重点的情况,直接暴力即可,复杂度$O(msqrt m)$。对于含有轻点的三元环,$O(m)$枚举第一个点及一条出边,$O(sqrt m)$枚举第二条出边,复杂度还是$O(msqrt m)$。这里对于边权的查询应该是利用哈希实现的,但是用map也能过,复杂度$O(msqrt mlog m)$。

     1 #include<map>
     2 #include<cmath>
     3 #include<cstdio>
     4 #include<cctype>
     5 #include<cstring>
     6 typedef long long int64;
     7 inline int getint() {
     8     register char ch;
     9     while(!isdigit(ch=getchar()));
    10     register int x=ch^'0';
    11     while(isdigit(ch=getchar())) x=(((x<<2)+x)<<1)+(ch^'0');
    12     return x;
    13 }
    14 inline int gettype() {
    15     register char ch;
    16     while(!isalpha(ch=getchar()));
    17     return ch!='R'?ch!='G'?0:1:2;
    18 }
    19 const int N=5e4+1,M=2e5,mod=1e9+7;
    20 struct Edge {
    21     int to,w,type,next;
    22 };
    23 Edge e[M];
    24 int h[N],sz,deg[N],c[N];
    25 struct Node {
    26     int u,v,type;
    27     bool operator < (const Node &another) const {
    28         if(u!=another.u) return u<another.u;
    29         if(v!=another.v) return v<another.v;
    30         return type<another.type;
    31     }
    32 };
    33 std::map<Node,int> map;
    34 inline void add_edge(const int &u,const int &v,const int &w,const int &t) {
    35     e[sz]=(Edge){v,w,t,h[u]};h[u]=sz++;deg[u]++;
    36     (map[(Node){u,v,t}]+=w)%=mod;
    37 }
    38 int main() {
    39     memset(h,-1,sizeof h);
    40     const int n=getint(),m=getint(),block=sqrt(m);
    41     for(register int i=0;i<m;i++) {
    42         const int u=getint(),v=getint(),w=getint(),t=gettype();
    43         add_edge(u,v,w,t);
    44         add_edge(v,u,w,t);
    45     }
    46     for(register int i=1;i<=n;i++) {
    47         if(deg[i]>=block) c[++c[0]]=i;
    48     }
    49     int ans=0;
    50     for(register int i=1;i<=c[0];i++) {
    51         for(register int j=1;j<=c[0];j++) {
    52             for(register int k=1;k<=c[0];k++) {
    53                 (ans+=(int64)map[(Node){c[i],c[j],0}]*map[(Node){c[j],c[k],1}]%mod*map[(Node){c[k],c[i],2}]%mod)%=mod;
    54             }
    55         }
    56     }
    57     for(register int i=1;i<=n;i++) {
    58         if(deg[i]>=block) continue;
    59         for(register int j=h[i];~j;j=e[j].next) {
    60             if(deg[e[j].to]<block&&e[j].to<=i) continue;
    61             for(register int k=e[j].next;~k;k=e[k].next) {
    62                 if(e[j].type==e[k].type||(deg[e[k].to]<block&&e[k].to<=i)) continue;
    63                 (ans+=(int64)map[(Node){e[j].to,e[k].to,3-e[j].type-e[k].type}]*e[j].w%mod*e[k].w%mod)%=mod;
    64             }
    65         }
    66     }
    67     printf("%d
    ",ans);
    68     return 0;
    69 }
  • 相关阅读:
    delphi7 stringgrid 点列头排序
    如何作为一个优秀的ERP实施顾问
    小米生态链去年收入150亿,今年目标200亿
    msys2 安装笔记(可以按照这个关键字搜索)
    MinGW 编译 libsndfile-1.0.25(只要有 MSYS,./configure make make install 就行了)
    Apache Ignite——新一代数据库缓存系统
    VS2015 C#6.0
    Webuploader 大文件分片上传
    requirejs
    require.js
  • 原文地址:https://www.cnblogs.com/skylee03/p/8694012.html
Copyright © 2020-2023  润新知