2017 清北济南考前刷题Day 3 afternoon
期望得分:100+40+100=240
实际得分:100+40+100=240

将每个联通块的贡献乘起来就是答案
如果一个联通块的边数>点数 ,那么无解
如果边数=点数,那么贡献是 2
如果边数=点数-1,那么贡献是点数
#include<queue>
#include<cstdio>
#include<iostream> using namespace std; const int mod=1e9+; #define N 100001 int front[N],to[N<<],nxt[N<<],tot; bool vis[N]; int d[N]; queue<int>q; int ans=; void read(int &x)
{
x=; char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) { x=x*+c-''; c=getchar(); }
} void add(int u,int v)
{
to[++tot]=v; nxt[tot]=front[u]; front[u]=tot;
to[++tot]=u; nxt[tot]=front[v]; front[v]=tot;
d[v]++;
} bool bfs(int s)
{
while(!q.empty()) q.pop();
int p=,e=;
q.push(s); vis[s]=true;
int now;
while(!q.empty())
{
now=q.front(); q.pop();
p++; e+=d[now];
for(int i=front[now];i;i=nxt[i])
if(!vis[to[i]]) vis[to[i]]=true,q.push(to[i]);
}
if(e>p) return false;
if(e==p) ans=ans*%mod;
else ans=1ll*ans*p%mod;
return true;
} int main()
{
freopen("girl.in","r",stdin);
freopen("girl.out","w",stdout);
int n,m;
read(n); read(m);
int u,v;
for(int i=;i<=m;i++)
{
read(u); read(v);
add(u,v);
}
for(int i=;i<=n;i++)
if(!vis[i])
if(!bfs(i)) { cout<<; return ; }
cout<<ans;
return ;
}

显然的结论:
若一个数的K进制和-k进制相同
那么他的k进制/-k进制的偶数位一定是0
然后乱搞就好了
也可以数位DP
#include<iostream>
#include<cstdio>
#include<cmath> using namespace std; typedef long long LL; LL bit[]; int a[]; int main()
{
freopen("endless.in","r",stdin);
freopen("endless.out","w",stdout);
long long n;int k;LL ans=;
scanf("%I64d%d",&n,&k);
int len=;
while(n) a[++len]=n%k,n/=k;
if(!(len&))
{
ans=pow(1LL*k,len/);
cout<<ans;
}
else
{
for(int i=len;i>=;i--)
if(a[i])
{
if(!(i&)) { ans+=pow(1LL*k,i/); break; }
ans+=1LL*a[i]*pow(1LL*k,i/);
if(i==) ans++;
}
cout<<ans;
}
}
40暴力
#include<cmath>
#include<cstdio>
#include<cstring>
#include<iostream> using namespace std; int fbit[]; int a[],b[]; int pre[]; int main()
{
freopen("endless.in","r",stdin);
freopen("endless.out","w",stdout);
int n,k;
scanf("%d%d",&n,&k);
fbit[]=;
int la,lb; int x,ans=min(k-,n)+;
for(int i=k;i<=n;i++)
{
la=;
x=i;
while(x) a[la++]=x%k,x/=k; la--;
x=i;
int c=-,now=;
pre[]=k-;
while()
{
fbit[++now]=fbit[now-]*c*k;
if(!(now&))
{
pre[now]=pre[now-]+(k-)*fbit[now];
if(pre[now]>=x) break;
}
else pre[now]=pre[now-];
}
lb=now;
memset(b,,sizeof(b));
while(now)
{
if(!(now&)) while(x>pre[now-]) b[now]++,x-=fbit[now];
else
{
while(x< && abs(x)>pre[now-]) b[now]++,x-=fbit[now];
while(x>pre[now-]) b[now]++,x+=fbit[now];
}
now--;
}
b[]=x;
if(la!=lb) continue;
bool ok=true;
for(int i=;i<=la && ok ;i++) if(a[i]!=b[i]) ok=false;
if(!ok) continue;
// printf("%d\n",i);
ans++;
}
cout<<ans;
}

考场思路:
每次旅行一定是找当前贡献最大的叶子节点
用线段树维护所有的叶子节点的贡献
修改:
每个点只会修改一次
所以用并查集记录这个点到根节点路径上第一个没有被修改的点
修改沿着并查集的father找上去
对于每个要改的点,预处理出它会影响到的叶子节点,
按dfs到的叶子节点的顺序在线段树中加点,那每个点影响到的叶子节点就是一段连续的区间
dfs记下来,线段树区间修改即可
其实可以不用并查集
往上改到已经改过的点,直接break
#include<cstdio>
#include<iostream>
#include<algorithm> using namespace std; #define N 100001 typedef long long LL; int n,m;
int val[N]; int front[N],nxt[N<<],to[N<<],tot; int F[N],fa[N],id[N]; int cnt,L[N],R[N]; LL w[N]; LL mx[N<<],pos[N<<],tag[N<<]; void read(int &x)
{
x=; char c=getchar();
while(!isdigit(c)) c=getchar();
while(isdigit(c)) { x=x*+c-''; c=getchar(); }
} void add(int u,int v)
{
to[++tot]=v; nxt[tot]=front[u]; front[u]=tot;
to[++tot]=u; nxt[tot]=front[v]; front[v]=tot;
} void init()
{
read(n); read(m);
for(int i=;i<=n;i++) read(val[i]);
int u,v;
for(int i=;i<n;i++)
{
read(u); read(v);
add(u,v);
}
} void dfs(int x,int f,LL sum)
{
L[x]=cnt+;
F[x]=x; bool leaf=true;
for(int i=front[x];i;i=nxt[i])
if(to[i]!=f) leaf=false,fa[to[i]]=x,dfs(to[i],x,sum+val[to[i]]);
if(leaf) w[++cnt]=sum,id[cnt]=x;
R[x]=cnt;
} void build(int k,int l,int r)
{
if(l==r) { mx[k]=w[l]; pos[k]=l; return; }
int mid=l+r>>;
build(k<<,l,mid);
build(k<<|,mid+,r);
mx[k]=max(mx[k<<],mx[k<<|]);
pos[k]= mx[k]==mx[k<<] ? pos[k<<] : pos[k<<|];
} void down(int k)
{
mx[k<<]-=tag[k];
mx[k<<|]-=tag[k];
tag[k<<]+=tag[k];
tag[k<<|]+=tag[k];
tag[k]=;
} void change(int k,int l,int r,int opl,int opr,LL sum)
{
if(l>=opl && r<=opr)
{
mx[k]-=sum;
tag[k]+=sum;
return;
}
if(tag[k]) down(k);
int mid=l+r>>;
if(opl<=mid) change(k<<,l,mid,opl,opr,sum);
if(opr>mid) change(k<<|,mid+,r,opl,opr,sum);
mx[k]=max(mx[k<<],mx[k<<|]);
pos[k]=mx[k]==mx[k<<] ? pos[k<<] : pos[k<<|];
} int find(int i) { return F[i]==i ? i : F[i]=find(F[i]); } void solve()
{
int p; LL ans=;
while(m--)
{
p=id[pos[]]; // 第pos个叶子节点
ans+=mx[];
while(p)
{
change(,,cnt,L[p],R[p],val[p]);
F[p]=find(F[fa[p]]);
p=F[p];
}
}
cout<<ans;
} int main()
{
freopen("tour.in","r",stdin);
freopen("tour.out","w",stdout);
init();
dfs(,,val[]);
build(,,cnt);
solve();
}
2017 清北济南考前刷题Day 3 afternoon的更多相关文章
- 2017 清北济南考前刷题Day 7 afternoon
期望得分:100+100+30=230 实际得分:100+100+30=230 1. 三向城 题目描述 三向城是一个巨大的城市,之所以叫这个名字,是因为城市中遍布着数不尽的三岔路口.(来自取名力为0的 ...
- 2017 清北济南考前刷题Day 1 afternoon
期望得分:80+30+70=180 实际得分:10+30+70=110 T1 水题(water) Time Limit:1000ms Memory Limit:128MB 题目描述 LYK出了道水 ...
- 2017 清北济南考前刷题Day 4 afternoon
期望得分:30+50+30=110 实际得分:40+0+0=40 并查集合并再次写炸... 模拟更相减损术的过程 更相减损术,差一定比被减数小,当被减数=减数时,停止 对于同一个减数来说,会被减 第1 ...
- 2017 清北济南考前刷题Day 6 afternoon
期望得分:100+100+30=230 实际得分: 正解: 枚举最高的位,这一位m是1但实际用了0 然后剩余的低位肯定是 正数就用1,负数用0 考场思路:数位DP #include<cstdio ...
- 2017 清北济南考前刷题Day 5 afternoon
期望得分:100+100+30=230 实际得分:0+0+0=30 T1 直接模拟 #include<cstdio> #include<iostream> using name ...
- 2017 清北济南考前刷题Day 2 afternoon
期望得分:100+60+70=230 实际得分:0+60+0=60 T1 可以证明如果一对括号原本就匹配,那么这对括号在最优解中一定不会被分开 所以用栈记录下没有匹配的括号 最后栈中一定是 一堆右括号 ...
- 2017 清北济南考前刷题Day 3 morning
实际得分:100+0+0=100 T1 右上角是必败态,然后推下去 发现同行全是必胜态或全是必败态,不同行必胜必败交叉 列同行 所以n,m 只要有一个是偶数,先手必胜 #include<cstd ...
- 2017 清北济南考前刷题Day 7 morning
期望得分:100+50+20=170 实际得分:10+50+20=80 1. 纸牌 题目描述 在桌面上放着n张纸牌,每张纸牌有两面,每面都写着一个非负整数.你的邪王真眼可以看到所有牌朝上的一面和朝下的 ...
- 2017 清北济南考前刷题Day 6 morning
T1 贪心 10 元先找5元 20元 先找10+5,再找3张5 #include<cstdio> using namespace std; int m5,m10,m20; int main ...
随机推荐
- Ubantu16.04进行Android 8.0源码编译
参考这篇博客 经过测试,8.0源码下载及编译之后,占用100多G的硬盘空间,尽量给ubantu系统多留一些硬盘空间,如果后续需要在编译好的源码上进行开发,需要预留更多的控件,为了防止后续出现文件权限问 ...
- BZOJ 2683: 简单题(CDQ分治 + 树状数组)
BZOJ2683: 简单题(CDQ分治 + 树状数组) 题意: 你有一个\(N*N\)的棋盘,每个格子内有一个整数,初始时的时候全部为\(0\),现在需要维护两种操作: 命令 参数限制 内容 \(1\ ...
- 【BZOJ1499】瑰丽华尔兹(动态规划)
[BZOJ1499]瑰丽华尔兹(动态规划) 题面 BZOJ 题解 先写部分分 设\(f[t][i][j]\)表示当前在\(t\)时刻,位置在\(i,j\)时走的最多的步数 这样子每一步要么停要么走 时 ...
- 【BZOJ1207】【HNOI2004】打鼹鼠(动态规划)
[BZOJ1207][HNOI2004]打鼹鼠 题面 BZOJ题面 题解 考虑到m的范围只有10000 O(m^2)的复杂度是可以接受的 所以直接暴力DP 每次枚举前面出现的鼹鼠 检查是否能够转移过来 ...
- LightOJ1282 Leading and Trailing
题面 给定两个数n,k 求n^k的前三位和最后三位 Input Input starts with an integer T (≤ 1000), denoting the number of test ...
- datatable 多字段 排序;
没有找到datatable的排序方面运用案例,根据接口,自己实现 所以记录一二,小伙伴们有更好的方法,欢迎讨论 1.需求图 2.需求 1)默认 未开启 灰色下箭头 2)第一次点击 :启动排序,降序- ...
- Android RecyclerView 滚动到中间位置
最近看到QQ音乐的歌词每次滑动后都可以滚回到中间位置.觉得甚是神奇,打开开发者模式显示布局,发现歌词部分不是采用 android 控件的写的,应该是前端写的.于是,我想,能不能用 recyclerVi ...
- windows下编译caffe报错:error MSB4062: 未能从程序集 E:\NugetPackages\OpenCV.2.4.10\......的解决办法
参考博客:http://blog.csdn.net/u013277656/article/details/75040459 在windows上编译caffe时,用vs打开后会自动加载还原NugetPa ...
- QBlog V2.5 源码开放下载(ASP.NET 番外系列之开端)
QBlog简介: QBlog:是一个套博客系统,开源.支持多用户.多语言.及方便的多数据库切换. QBlog下载:http://www.cyqdata.com/download/article-det ...
- 本地安装plsql和instantclient连接linux服务器端的oracle
当虚拟机里面的linux服务器安装好oracle之后(具体安装方法在之前的博客有说到),如何连接使用呢?连接过程中会出现什么问题呢? 1.首先我们下载instantclient的压缩包,直接解压就好, ...