距离杯赛已经很久了,然而我现在才打总结。。

我好惨的说..两场才380。。。


DAY 1

第一题 toy

送分题,模拟的时候+一下再mod一下就好。

[当时打完这题就没再看一眼了,好方的说]

#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define Maxn 100010 int a[Maxn];
char s[Maxn][]; int main()
{
int n,m;
scanf("%d%d",&n,&m);
for(int i=;i<n;i++)
{
scanf("%d",&a[i]);
scanf("%s",s[i]);
}
int now=;
for(int i=;i<=m;i++)
{
int x,y;
scanf("%d%d",&x,&y);
y%=n;
if(a[now]==&&x==) now=(now+y)%n;
else if(a[now]==) now=(now+n-y)%n;
else if(x==) now=(now+n-y)%n;
else now=(now+y)%n;
}
printf("%s\n",s[now]);
return ;
}

第二题 running

感觉这题是全场最难的【是吧??

但其实【啊好像也不是很难。。

怎么比赛的时候就脑子那么乱呢

我的方法是,把路径分成两段,然后lca的特殊算。

假如lca在st上面,假设这条路径对z有贡献(z在lca和st之间),那么dep[z]-dep[st]=w[z]   =>  dep[z]-w[z]=dep[st]

那么对于z来说,就是求经过自己的路径中dep等于dep[z]-w[z]的有多少个。

对于路径,我们在st上打一个加入标记,在lca上打一个删除标记,那么对于z,就是求其子树和(每个点用dfs序做,问题变成求区间和,单点修改,区间询问,可以用树状数组维护)。

对于加入和删除,我们按照st的dep排序,对于每个点,我们按照dep[z]-dep[st]排序,值相等是一起做,这时O(n+m)的。

对于右半边的路径类似,有2*dep[lca]-dep[st]=dep[z]+w[z]。

#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
#define Maxn 300010
#define Maxm 300010 struct node
{
int x,y,next,c;
}t[Maxn*];int len=;
int n,m; struct hp
{
int x,y,c;
}q[Maxm],qq[Maxm],nq[Maxn];
int l1,l2; int first[Maxn]; void ins(int x,int y)
{
t[++len].x=x;t[len].y=y;
t[len].next=first[x];first[x]=len;
} bool cmp(hp x,hp y) {return x.c<y.c;} int son[Maxn],dep[Maxn],sm[Maxn];
int fa[Maxn];
void dfs(int x,int f)
{
sm[x]=;dep[x]=dep[f]+;
fa[x]=f;
son[x]=;
for(int i=first[x];i;i=t[i].next) if(t[i].y!=f)
{
int y=t[i].y;
dfs(y,x);
sm[x]+=sm[y];
if(sm[y]>sm[son[x]]) son[x]=y;
}
} int tp[Maxn],dfn[Maxn],rt[Maxn],cnt=;
void dfs2(int x,int tpp)
{
tp[x]=tpp;rt[x]=dfn[x]=++cnt;
if(son[x]) dfs2(son[x],tpp),rt[x]=rt[son[x]];
for(int i=first[x];i;i=t[i].next) if(t[i].y!=fa[x]&&t[i].y!=son[x])
{
int y=t[i].y;
dfs2(y,y);
rt[x]=rt[y];
}
} int lca(int x,int y)
{
int tt;
while(tp[x]!=tp[y])
{
if(dep[tp[x]]<dep[tp[y]]) tt=x,x=y,y=tt;
x=fa[tp[x]];
}
if(dep[x]<dep[y]) return x;
return y;
} int w[Maxn],ans[Maxn],c[Maxn]; void add(int x,int y)
{
for(int i=x;i<=n;i+=i&(-i))
c[i]+=y;
} int query(int l,int r)
{
int ans=;
for(int i=r;i>=;i-=i&(-i))
ans+=c[i];
l--;
for(int i=l;i>=;i-=i&(-i))
ans-=c[i];
return ans;
} void ffind()
{
int l,r;
l=,r=;
memset(c,,sizeof(c));
for(int i=;i<=n;i++)
{
int x=nq[i].x;
if(i==||nq[i].c!=nq[i-].c)
{
for(int j=l;j<r;j++)
{
add(q[j].x,-),add(q[j].y,);
}
l=r;
while(q[l].c<nq[i].c&&l<=l1) l++;
r=l;
}
while(q[r].c==nq[i].c&&r<=l1)
{
add(q[r].x,);add(q[r].y,-);
//printf("add %d\n",r);
r++;
}
ans[x]+=query(dfn[x],rt[x]);
}
} int main()
{
scanf("%d%d",&n,&m);
for(int i=;i<n;i++)
{
int x,y;
scanf("%d%d",&x,&y);
ins(x,y);ins(y,x);
}
for(int i=;i<=n;i++) scanf("%d",&w[i]);
dfs(,);
dfs2(,);
l1=l2=;
memset(ans,,sizeof(ans));
for(int i=;i<=m;i++)
{
int x,y,z;
scanf("%d%d",&x,&y);
z=lca(x,y);
q[++l1].x=dfn[x];q[l1].y=dfn[z];q[l1].c=dep[x];
qq[++l2].x=dfn[y];qq[l2].y=dfn[z];qq[l2].c=*dep[z]-dep[x]; if(w[z]==dep[x]-dep[z]) ans[z]++;
}
sort(q+,q++l1,cmp);
for(int i=;i<=n;i++) nq[i].x=i,nq[i].c=dep[i]+w[i];
sort(nq+,nq++n,cmp);
ffind(); for(int i=;i<=l2;i++) q[i]=qq[i];
l1=l2;
sort(q+,q++l1,cmp);
for(int i=;i<=n;i++) nq[i].x=i,nq[i].c=dep[i]-w[i];
sort(nq+,nq++n,cmp);
ffind(); for(int i=;i<=n;i++) printf("%d ",ans[i]);
printf("\n");
return ;
}

第三题 classroom

其实是一个很明显的期望DP。【当时脑抽again = = toxic

状态f[i][j][0]表示前i段,用j次机会,最后一次不使用机会的期望值。

状态f[i][j][1]表示前i段,用j次机会,最后一次使用机会的期望值。

f[i][j][0]=min(f[i-1][j][0]+1.0*dis[c[i-1]][c[i]])

f[i][j][0]=min(f[i-1][j][1]+1.0*dis[d[i-1]][c[i]]*k[i-1]+(1-k[i-1])*dis[c[i-1]][c[i]]);

f[i][j][1]=min(f[i-1][j-1][0]+k[i]*(dis[c[i-1]][d[i]])+(1-k[i])*(dis[c[i-1]][c[i]]));

f[i][j][1]=min(f[i-1][j-1][1]+ k[i]*(dis[d[i-1]][d[i]]*k[i-1]+dis[c[i-1]][d[i]]*(1-k[i-1]))+ (1-k[i])*(dis[d[i-1]][c[i]]*k[i-1]+dis[c[i-1]][c[i]]*(1-k[i-1])));

 #include<cstdio>
#include<cstdlib>
#include<cstring>
#include<iostream>
#include<queue>
#include<algorithm>
using namespace std;
#define Maxn 2010
#define INF 0xfffffff int c[Maxn],d[Maxn];
double f[Maxn][Maxn][],k[Maxn]; int n,m,v,e; int mmin(int x,int y) {return x<y?x:y;}
double mymin(double x,double y) {return x<y?x:y;} int dis[Maxn][Maxn]; void floyd()
{
for(int l=;l<=v;l++)
for(int i=;i<=v;i++)
for(int j=;j<=v;j++)
dis[i][j]=mmin(dis[i][j],dis[i][l]+dis[l][j]);
} int main()
{
scanf("%d%d%d%d",&n,&m,&v,&e);
for(int i=;i<=n;i++) scanf("%d",&c[i]);
for(int i=;i<=n;i++) scanf("%d",&d[i]);
for(int i=;i<=n;i++) scanf("%lf",&k[i]);
memset(dis,,sizeof(dis));
for(int i=;i<=e;i++)
{
int x,y,c;
scanf("%d%d%d",&x,&y,&c);
dis[x][y]=mmin(dis[x][y],c);
dis[y][x]=mmin(dis[y][x],c);
}
for(int i=;i<=v;i++) dis[i][i]=;
floyd(); for(int i=;i<=n;i++)
for(int j=;j<=n;j++)
f[i][j][]=f[i][j][]=INF;
double ans=INF;
f[][][]=f[][][]=;f[][][]=;
for(int i=;i<=n;i++)
for(int j=;j<=i&&j<=m;j++)
{
//printf("%.2lf\n",ans);
//bu yong
f[i][j][]=mymin(f[i][j][],f[i-][j][]+1.0*dis[c[i-]][c[i]]);
f[i][j][]=mymin(f[i][j][],f[i-][j][]+1.0*dis[d[i-]][c[i]]*k[i-]+(-k[i-])*dis[c[i-]][c[i]]); //yong
if(j>)
{
f[i][j][]=mymin(f[i][j][],f[i-][j-][]+k[i]*(dis[c[i-]][d[i]])+(-k[i])*(dis[c[i-]][c[i]]));
f[i][j][]=mymin(f[i][j][],f[i-][j-][]+
k[i]*(dis[d[i-]][d[i]]*k[i-]+dis[c[i-]][d[i]]*(-k[i-]))+
(-k[i])*(dis[d[i-]][c[i]]*k[i-]+dis[c[i-]][c[i]]*(-k[i-])));
}
}
for(int i=;i<=m&&i<=n;i++) ans=mymin(ans,f[n][i][]),
ans=mymin(ans,f[n][i][]);
printf("%.2lf\n",ans);
return ;
}

第一天 100+25+55 哭泣

第二题交了纯暴力,第三题错误DP。。


DAY 2

第一题 problem

用杨辉三角搞一搞就好了。

 #include<cstdio>
#include<cstdlib>
#include<cstring>
#include<algorithm>
#include<iostream>
using namespace std;
#define Maxn 2010 int p[Maxn],f[Maxn][Maxn];
int k; int c[Maxn][Maxn],ans[Maxn][Maxn]; void init()
{
for(int i=;i<=;i++) c[i][]=;
for(int i=;i<=;i++)
for(int j=;j<=i;j++)
c[i][j]=(c[i-][j-]+c[i-][j])%k; memset(f,,sizeof(f));
for(int i=;i<=;i++)
{
f[i][]=;
for(int j=;j<=i;j++)
{
f[i][j]=f[i][j-];
if(c[i][j]==) f[i][j]++;
}
for(int j=i+;j<=;j++) f[i][j]=f[i][j-];
}
for(int i=;i<=;i++) ans[][i]=f[][i];
for(int i=;i<=;i++)
for(int j=;j<=;j++) ans[i][j]=ans[i-][j]+f[i][j];
} int main()
{
int T;
scanf("%d%d",&T,&k);
init();
while(T--)
{
int n,m;
scanf("%d%d",&n,&m);
printf("%d\n",ans[n][m]);
}
return ;
}

第二题 earthworm

在暴力的基础上看出来有单调性就可以AC了。

切出来的左边递减,右边也递减,每次取三部分的最大值出来切,注意不要想成全部+q,用一个累加器,然后切出来的那部分-q是一样的。

//代码很丑,因为在洛谷上调TLE,,洛谷好慢的说。。

 #include<cstdio>
#include<cstdlib>
#include<cstring>
#include<algorithm>
#include<iostream>
using namespace std;
#define Maxn 100010
#define Maxm 7000010
#define INF 0xfffffff
#define LL long long int a[Maxn]; LL add=;
LL v1[Maxm],v2[Maxm]; int n,m,q,u,v,t;
int l1,l2; bool cmp(int x,int y) {return x>y;} int main()
{
scanf("%d%d%d%d%d%d",&n,&m,&q,&u,&v,&t);
for(int i=;i<=n;i++) scanf("%d",&a[i]);
sort(a+,a++n,cmp);
l1=,l2=;
v1[]=v2[]=;
a[]=;
for(LL i=;i<=m;i++)
{ LL now=-INF;
now*=;
if(a[]<=n) now=now>a[a[]]?now:a[a[]];
if(l1<=v1[]) now=now>v1[l1]?now:v1[l1];
if(l2<=v2[]) now=now>v2[l2]?now:v2[l2];
if(a[]<=n&&now==a[a[]]) a[]++;
else if(l1<=v1[]&&now==v1[l1]) l1++;
else if(l2<=v2[]&&now==v2[l2]) l2++;
now+=add; if(i%t==) printf("%lld ",now);
add+=q;
LL x=now*u/v,y=now-x;
v1[++v1[]]=x-add;v2[++v2[]]=y-add;
}
printf("\n");
for(int i=;i<=n+m;i++)
{ LL now=-INF;
now*=;
if(a[]<=n) now=now>a[a[]]?now:a[a[]];
if(l1<=v1[]) now=now>v1[l1]?now:v1[l1];
if(l2<=v2[]) now=now>v2[l2]?now:v2[l2];
if(a[]<=n&&now==a[a[]]) a[]++;
else if(l1<=v1[]&&now==v1[l1]) l1++;
else if(l2<=v2[]&&now==v2[l2]) l2++;
now+=add; if(i%t==) printf("%lld ",now);
}
printf("\n");
return ;
}

第三题 angrybirds

其实就是状压dp啊

注意精度,不要*100然后强转int【我就死在强转int,不然用round也可以

还有一个小地方就是,你可能会枚举两个点,是18^2的,但是其实你可以只枚举一个点,规定这一次一定先把某头猪弄下来(因为你后面总有一次要把这头猪弄下来的,不如现在先做了,反正没什么区别),这样就是一个18,这样就可以过了。

 #include<cstdio>
#include<cstdlib>
#include<cstring>
#include<algorithm>
#include<iostream>
using namespace std;
#define Maxd 300010
#define INF 0xfffffff double xx[],yy[]; int f[Maxd];
int n,m; int gcd(int a,int b)
{
if(b==) return a;
return gcd(b,a%b);
} double fabs(double x) {return x<?-x:x;} int sum;
int get_s(int a,int b,int s)
{
int ss=s;
double A,B;
A=(xx[b]*yy[a]-xx[a]*yy[b])*1.0/(xx[b]*xx[a]*xx[a]-xx[a]*xx[b]*xx[b]);
B=(yy[a]-A*xx[a]*xx[a])*1.0/xx[a];
if(A>=)
{
return -;
}
sum=;
for(int i=;i<=n;i++) if((<<i-)&s)
{
if(fabs(A*xx[i]*xx[i]+B*xx[i]-yy[i])<0.000001) ss^=(<<i-),sum++;
}
return ss;
} int mymin(int x,int y) {return x<y?x:y;} int ffind(int s)
{
if(f[s]!=-) return f[s];
f[s]=INF;
for(int i=;i<=n;i++) if((<<i-)&s)
{
for(int j=i+;j<=n;j++) if((<<j-)&s)
{
int ss=get_s(i,j,s);
if(ss!=-) f[s]=mymin(f[s],ffind(ss)+);
}
break;
}
for(int i=;i<=n;i++) if((<<i-)&s)
{
f[s]=mymin(f[s],ffind(s-(<<i-))+);
break;
}
return f[s];
} int main()
{
int T;
scanf("%d",&T);
while(T--)
{
scanf("%d%d",&n,&m);
for(int i=;i<=n;i++)
{
double nx,ny;
scanf("%lf%lf",&nx,&ny);
xx[i]=nx;yy[i]=ny;
}
memset(f,-,sizeof(f));
f[]=;
int ans=ffind((<<n)-);
printf("%d\n",ans);
}
return ;
}

第二天 100+55+70 哭泣


被虐的好惨,主要是还是太傻了,其实题目说难也不是很难的。。。。

上面是bac回的AC代码。。。。

2016-12-07 14:02:45

【NOIP 2016 总结】的更多相关文章

  1. NOIp 2016 总结

    NOIp 2016 总结 -----YJSheep Day 0 对于考前的前一天,晚自习在复习图论的最短路和生成树,加深了图的理解.睡得比较早,养足精力明日再战. Day 1 拿到题目,先过一边,题目 ...

  2. 【NOIP 2016】斗地主

    题意 NOIP 2016 斗地主 给你一些牌,按照斗地主的出牌方式,问最少多少次出完所有的牌. 分析 这道题的做法是DFS. 为了体现这道题的锻炼效果,我自己写了好多个代码. Ver1 直接暴力搞,加 ...

  3. [NOIP]2016天天爱跑步

    [NOIP]2016天天爱跑步 标签: LCA 树上差分 NOIP Description 小C同学认为跑步非常有趣,于是决定制作一款叫做<天天爱跑步>的游戏.<天天爱跑步>是 ...

  4. NOIP 2016 迟来的满贯

    17-03-22,雨 17-03-22,一个特别重要的日子 在这一天,本蒻攻克了NOIP 2016最难的一题,D1T2——天天爱跑步 实现了NOIP 2016的AK! YAYAYAYAYAYAY 自然 ...

  5. NOIP 2016 D2T2 蚯蚓](思维)

    NOIP 2016 D2T2 蚯蚓 题目大意 本题中,我们将用符号 \(\lfloor c \rfloor⌊c⌋\) 表示对 \(c\) 向下取整,例如:\(\lfloor 3.0 \rfloor = ...

  6. Noip 2016 Day 1 & Day 2

    Day 1 >>> T1 >> 水题直接模拟AC: 考察三个知识点:1.你能不能编程 2.你会不会取模 3.你脑子抽不抽 然而第一次评测还是90,因为当模运算时 “ en ...

  7. 清北 Noip 2016 考前刷题冲刺济南班

    2016 10 29 周六 第一天 %%%,%ZHX大神 上午,60分, 下午,爆零orz 2016 10 30 周天 第二天 炒鸡倒霉的一天 %%%,%ZHX大神 据大神第一天的题最简单. 上午,和 ...

  8. Noip 2016

    Day1 思路: 大致是 把一个环拆成链, 找某个人无非是向右找或向左找(即对当前点加或减) 若加上要移动的位置后坐标大于总人数, 就把当前坐标减去总人数, 若减去要移动的位置后坐标小于0, 就把当前 ...

  9. noip 2016 提高组题解

    前几天写的那个纯属搞笑.(额,好吧,其实这个也不怎么正经) 就先说说day2吧: T1:这个东西应该叫做数论吧. 然而我一看到就照着样例在纸上推了大半天(然而还是没有看出来这东西是个杨辉三角) 然后就 ...

  10. noip 2016 提高组总结(不是题解)

    小弱鸡杨树辰是第一次参加像noip这样的高大上的比赛,于是他非常,非常,非常激动. 当他第二天考完试后,他正在yy自己的分数:day1T1应该是a掉了,T2写了个30分的暴力,T3也是个40分的暴力, ...

随机推荐

  1. Cocos2d-x加速度计实例:运动的小球

    下面我们通过一个实例介绍一下如果通过层加速度计事件实现访问加速度计.该实例场景如下图所示,场景中有一个小球,当我们把移动设备水平放置,屏幕向上,然后左右晃动移动设备来改变小球的位置. 下面我们再看看具 ...

  2. 在swift中使用MJRefresh

    cocoapod导入的,并且桥接已经完成,但是就是不提示方法,醉了,

  3. (转)实战Memcached缓存系统(5)Memcached的CAS程序实例

    1. 非CAS 首先看一个不是CAS的Memcached程序实例.实例的问题原型,见上一篇博文. 程序实例: package com.sinosuperman.memcached; import ja ...

  4. spring aop配置文档部分翻译

    欢迎转载交流: http://www.cnblogs.com/shizhongtao/p/3476973.html 下面的文字来自官方文档的翻译,具体事例以后奉上. Advisors "ad ...

  5. 彻底删除sql server的方法

    请先确定是否把sql相关的东西删了,建议进行如下操作. 1.先下个Windows Install Clean Up,清理sql相关东西,要全部清理. 2.到控制面板--添加删除程序中看是否还有未删的. ...

  6. OCP考试之052

    Oracle Database 11g:Administration I 考试时间:90分钟 考试题目:70题 考试语言:英语 考试分数:66% 考试内容: 了解Oracle数据库体系结构 解释的内存 ...

  7. 在emacs里用w3m浏览网页

    给w3m配置个~/.emacs老是暴错误,在配置里把这个注掉就OK了;(require 'mime-w3m) ;;支持w3m (add-to-list 'load-path "/usr/sh ...

  8. 1006. Sign In and Sign Out

    #include <stdio.h> #include <algorithm> #include <iostream> #include <string.h& ...

  9. FatMouse

      时间限制:1 秒 内存限制:128 兆 特殊判题:否 提交:1431 解决:641 题目描述: FatMouse prepared M pounds of cat food, ready to t ...

  10. Head of a Gang (map+邻接表+DFS)

    One way that the police finds the head of a gang is to check people's phone calls. If there is a pho ...