码迷,mamicode.com
首页 > 其他好文 > 详细

HL省选冲刺

时间:2020-06-13 21:01:59      阅读:74      评论:0      收藏:0      [点我收藏+]

标签:溢出   click   its   i++   如何   ret   main   class   aaa   

D-8

申请停课,ly说的还是很有道理的(虽然我也这么想),文化课什么的,早晚都得学,oi可能就学不了了(tcl),想做什么还是去做吧,也没什么不可能的(是吧,陈。 :)  )做了准备(虽然并不adequate,但是不尝试=100%GG,尝试=99%GG)有计划每天上午考试下午改题晚上改题。结果已经不重要了(学2年了快,挺有趣的)

D-7

停课D1,早自习了。上午各科老师问我干啥了,尴尬死。。。我以为ly说过了,给各位造成了不便。。。sorry。上午考试发现自己菜死了。sb题都不会了,analysis below

T1

技术图片

 

 (其他样例啥的就不写了,子任务)

先分析一下,一开始觉得期望,就没怎么看,后来看到了子任务有 只有一个边有权值,暗示我们这个题只需要一个一个边考虑就行。首先对于一条边,左边x*boy,y*girl,(右边m-x*boy,m-y*girl)然后左边子树size,(右边子树n-size)我们肯定想最大,最大的话就是min(x,m-y)+min(y,m-x) 这东西画画图发现=max(x+y,2m-x-y)

技术图片

 实际上问题就变成了,2m中选x个人(不分男女)然后瞎jb放

还有个点就是:根据调整法(我这么叫他)我们肯定能在保证一条边达到最大贡献 ,同时 ,让另一条边也达到最大 贡献,然后推广到所有边。

然后问题就愉快的变成了 sigma w[u,v]*c(2m,x)*size[u]^x*size[v]^(2m-x)*max(x,2m-x) (x=1~2m-1)瞎jb选x个人,瞎jb放在一边,然后瞎jb连边达到最大,然后就可以了。

技术图片
 1 #include<bits/stdc++.h>
 2 #define LL long long
 3 using namespace std;
 4 const int maxn=2505;
 5 const LL P=1e9+7ll;
 6 int Pow[maxn][maxn<<1];//pow[i][j]=i^j
 7 int sum[maxn];//sum[i]=sigma C(2m,j)i^j*(n-i)^(2m-j) (j=1~2m-1)
 8 int n,m;
 9 int w[maxn];
10 struct Edge{
11     int u,v;
12     Edge(int U=0,int V=0):u(U),v(V){}
13 }e[maxn];
14 int ans;
15 int fst[maxn],nxt[maxn<<1],to[maxn<<1],edge_count;
16 inline void add(int x,int y){
17     edge_count++;
18     to[edge_count]=y;
19     nxt[edge_count]=fst[x];
20     fst[x]=edge_count;
21 }
22 int size[maxn];
23 void dfs(int u,int fa){
24     size[u]=1;
25     for(int i=fst[u];i;i=nxt[i]){
26         int v=to[i];
27         if(v==fa)continue;
28         dfs(v,u);
29         size[u]+=size[v];
30     }
31 }
32 int jc[maxn<<1],inv[maxn<<1],njc[maxn<<1];
33 inline void com(){
34     inv[1]=jc[1]=njc[1]=jc[0]=njc[0]=1;
35     for(int i=2;i<=m<<1;i++){
36         jc[i]=1ll*jc[i-1]*i%P;
37         inv[i]=1ll*(P-P/i)*inv[P%i]%P;
38         njc[i]=1ll*njc[i-1]*inv[i]%P;
39     }
40 }
41 inline int c(int n,int m){return 1ll*jc[n]*njc[m]%P*njc[n-m]%P;}
42 inline void init(){
43     for(int i=1;i<n;i++){//ö¾Ù size & n-size 
44         Pow[i][0]=1;
45         for(int j=1;j<m<<1;j++)Pow[i][j]=1ll*Pow[i][j-1]*i%P;
46         //size^(x+y) & size^(2m-x-y)
47     }
48     for(int i=1;i<n;i++){//sum[size]=sigma size^(x+y)*(n-size)^(2m-x-y) (x+y = 1~2m-1)
49         for(int j=1;j<m<<1;j++)
50         sum[i]=(1ll*sum[i]+1ll*c(m<<1,j)*min(j,(m<<1)-j)%P*Pow[i][j]%P*Pow[n-i][(m<<1)-j]%P)%P;
51     }
52 }
53 int main(){
54     scanf("%d%d",&n,&m);
55     com();init();
56     for(int i=1,u,v;i<n;i++){
57         scanf("%d%d%d",&u,&v,&w[i]);
58         e[i]=Edge(u,v);
59         add(u,v);add(v,u);
60     }
61     dfs(1,0);
62     for(int i=1;i<n;i++){
63         ans=(1ll*ans+1ll*w[i]*sum[ min(size[e[i].u],size[e[i].v]) ])%P;
64     }
65     
66     printf("%d",ans);
67     return 0;
68 }
AC code

T2

挺sb的题,但是我想了好久,一开始发现,倍长(显然),枚举,判定,问题是如何判定,一直在想,如果 k 不合法,那么会在 相邻两个不相同的情况下 构成 f(k)个,相隔k个出现相同字符,(aaaaaaabaab,k=3(k的定义是,旋转的长度))然后想的是建边,跑topological sort,但是没办法,边长太多,不能直接搞。

经过qzh dalao启发,hash,冥思苦想 啊,hash判定字符串相等(重新推了一下 unsigned long long 自然溢出hash,真tm好用。),发现,刚刚自己一直想弄的,有f(k)个不合法子串<=>平移k位 重合。

技术图片 AC Code

 

HL省选冲刺

标签:溢出   click   its   i++   如何   ret   main   class   aaa   

原文地址:https://www.cnblogs.com/a-blog-of-taojiayi-2003/p/13121664.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!