[Codeforces #196] Tutorial
Link:
A:
枚举
#include <bits/stdc++.h> using namespace std;
#define X first
#define Y second
typedef long long ll;
typedef pair<int,int> P;
const int MAXN=1e5+;
int n,m,dat[MAXN],res=<<; int main()
{
scanf("%d%d",&n,&m);
for(int i=;i<=m;i++) scanf("%d",&dat[i]);
sort(dat+,dat+m+);
for(int i=;i<=m-n+;i++)
res=min(res,dat[i+n-]-dat[i]);
printf("%d",res);
return ;
}
Problem A
B:
可以发现分母为$max(a*d,b*c)$,分子为$|a*d-b*c|$
#include <bits/stdc++.h> using namespace std;
#define X first
#define Y second
typedef long long ll;
typedef pair<int,int> P;
int a,b,c,d,ta,tb,tc,td,resx,resy;
int GCD(int x,int y){return x%y==?y:GCD(y,x%y);} int main()
{
scanf("%d%d%d%d",&a,&b,&c,&d);
resx=abs(a*d-c*b),resy=max(a*d,c*b);
int gcd=GCD(resx,resy);
printf("%d/%d",resx/gcd,resy/gcd);
return ;
}
Problem B
C:
直接贪心,考虑将空格插入连续的序列中
如果可以不翻倍自然答案就是$m$,否则应当尽可能在前面翻倍来减少增加的分数
能推出翻倍$q$次后的分数为$(2^q-1)*2*k$,这样再加上剩余不翻倍的分数即可
#include <bits/stdc++.h> using namespace std;
#define X first
#define Y second
typedef long long ll;
typedef pair<int,int> P;
const ll MOD=1e9+;
ll n,m,k,res;
ll quick_pow(ll a,ll b)
{
ll ret=;
for(;b;b>>=,a=a*a%MOD)
if(b&) ret=ret*a%MOD;
return ret;
} int main()
{
scanf("%I64d%I64d%I64d",&n,&m,&k);
if(!m||!n) return puts(""),;
ll rst=n-m,num=n/k;
if(rst>=num) res=m;
else res=(quick_pow(,num-rst)-)**k%MOD+(m-(num-rst)*k%MOD);
printf("%I64d",(res+MOD)%MOD);
return ;
}
Problem C
D:
官方题解:
将原树转化成有根树,对于一个点的最远关键点分成两类:
1、在该点的子树中,记最远距离为$MaxDown$
2、在树上的其它部分,记最远距离为$MaxUp$
对于1,明显可以$dfs$通过孩子节点来更新
对于2,又要分为两类来更新:
1、在其兄弟节点的子树中,即$MaxDown_{sibling}+2$
2、不在父亲节点的子树中,即$MaxUp_{father}+1$
其中注意用兄弟节点更新时要先记录最大/次大值来保证$O(1)$更新
不过感觉我的方法更简单啊……
先想想如何求一个点到树上任意点的最远距离
明显是用数的直径来解决的经典问题,可用反证法证明最远点一定是直径的两端
发现将任意点改为特定的关键点后该结论依然成立!
因此只要找到关键点中最远的点对$(a,b)$,对于每个点$v$判断$dist(a,v),dist(b,v)\le d$
#include <bits/stdc++.h> using namespace std;
#define X first
#define Y second
typedef long long ll;
typedef pair<int,int> P;
const int MAXN=1e5+;
int head[MAXN],tot;
struct edge{int nxt,to;}e[MAXN<<];
int n,m,d,x,y,p[MAXN],rt1,rt2,d1[MAXN],d2[MAXN],res; void add(int from,int to)
{e[++tot].nxt=head[from];e[tot].to=to;head[from]=tot;}
void dfs(int x,int anc,int *d)
{
for(int i=head[x];i;i=e[i].nxt)
if(e[i].to!=anc)
d[e[i].to]=d[x]+,dfs(e[i].to,x,d);
} int main()
{
scanf("%d%d%d",&n,&m,&d);
for(int i=;i<=m;i++) scanf("%d",&p[i]);
for(int i=;i<n;i++)
scanf("%d%d",&x,&y),add(x,y),add(y,x); d1[]=;dfs(,,d1);
for(int i=;i<=m;i++) if(d1[p[i]]>d1[rt1]) rt1=p[i];
d1[rt1]=;dfs(rt1,,d1);
for(int i=;i<=m;i++) if(d1[p[i]]>d1[rt2]) rt2=p[i];
d2[rt2]=;dfs(rt2,,d2); for(int i=;i<=n;i++)
if(d1[i]<=d&&d2[i]<=d) res++;
printf("%d",res);
return ;
}
Problem D
虽说第一种解法可能代码量稍大,但分类方法还是很实用的:
将无根树转化成有根树后按照是否在该点的子树中分类
其中兄弟节点对该点的贡献不要忘记统计!我一开始就漏掉了……
E:
发现最优解除了叶子节点和根外,其它节点必然都属于$a$
考虑一个点向当前树插入,其要么接在某个节点后,要么重开一棵树
由于$n$只有8,明显排序预处理后枚举各种组合就好了
其中有一些技巧需要注意:
1、采取从根到叶子的构造更加方便
由于树根确定其叶子节点就已经确定,后面接点时就不用再考虑叶子节点的贡献了
2、不要漏考虑最大点本身就是根的情况,这样答案会减少1
#include <bits/stdc++.h> using namespace std;
#define X first
#define Y second
typedef long long ll;
typedef pair<int,int> P;
ll n,dat[],dvs[],res=1ll<<; void dfs(int k,int sum,int rt)
{
if(k==n+)
{res=min(res,sum+ll(rt>));return;}
if(dvs[k]>) sum++; dfs(k+,sum+dvs[k],rt+);//单独成树
for(int i=;i<k;i++)//连在之前的节点后
if(dat[i]%dat[k]==)
dat[i]/=dat[k],dfs(k+,sum,rt),dat[i]*=dat[k];
} int main()
{
scanf("%I64d",&n);
for(int i=;i<=n;i++) scanf("%I64d",&dat[i]);
sort(dat+,dat+n+,greater<ll>());
for(int i=;i<=n;i++)
{
ll t=dat[i];
for(int j=;1ll*j*j<=dat[i];j++)
while(t%j==) t/=j,dvs[i]++;
if(t>) dvs[i]++;
} dfs(,,);
printf("%I64d",res);
return ;
}
Problem E
[Codeforces #196] Tutorial的更多相关文章
- Codeforces 196 E. Tricky and Cleve Password
\(>Codeforces \space 196\ E. Tricky\ and\ Cleve\ Password<\) 题目大意 : 给出一个有 \(n\) 个结点,\(m\) 条边的连 ...
- [Codeforces #172] Tutorial
Link: Codeforces #172 传送门 A: 一眼看上去分两类就可以了 1.每个矩形只有两条边相交,重合的形状为菱形 2.每个矩形四条边都有相交 对于情况1答案为$h*h/sin(a)$ ...
- [Codeforces #514] Tutorial
Link: Codeforces #514 传送门 很简单的一场比赛打崩了也是菜得令人无话可说…… D: 一眼二分,发现对于固定的半径和点,能包含该点的圆的圆心一定在一个区间内,求出区间判断即可 此题 ...
- [Codeforces #210] Tutorial
Link: Codeforces #210 传送门 A: 贪心,对每个值都取最大值,不会有其他解使答案变优 #include <bits/stdc++.h> using namespace ...
- [Codeforces #174] Tutorial
Link: Codeforces #174 传送门 A: 求原根的个数,有一条性质是原根个数为$\phi(\phi(n))$,多了一个不会证的性质 如果要确定哪些是原根的话还是要枚举,不过对于每个数不 ...
- [Codeforces #190] Tutorial
Link: Codeforces #190 传送门 A: 明显答案为$n+m-1$且能构造出来 #include <bits/stdc++.h> using namespace std; ...
- [Codeforces #211] Tutorial
Link: Codeforces #211 传送门 一套非常简单的题目,但很多细节都是错了一次才能发现啊…… 还是不能养成OJ依赖症,交之前先多想想corner case!!! A: 模拟,要特判0啊 ...
- [Codeforces #192] Tutorial
Link: Codeforces #192 传送门 前两天由于食物中毒现在还要每天挂一天的水 只好晚上回来随便找套题做做找找感觉了o(╯□╰)o A: 看到直接大力模拟了 但有一个更简便的方法,复杂度 ...
- Codeforces 196 C. Paint Tree
分治.选最左上的点分给根.剩下的极角排序后递归 C. Paint Tree time limit per test 2 seconds memory limit per test 256 megaby ...
随机推荐
- PHP练习4 留言板
一.要求 二.示例页面 三.网页代码及网页显示 1.denglu.php 登录页面 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Tran ...
- bootstrap框架的搭建
bootstrap框架 Bootstrap,来自 Twitter,是目前最受欢迎的前端框架.Bootstrap 是基于 HTML.CSS.JAVASCRIPT 的,它简洁灵活,使得 Web 开发更加快 ...
- lua 闪电特效
闪电特效 根据不同的起点 终点 资源做倾斜 拉伸 ,主要是计算倾斜角度. function ZyLight:show(params) local params = params or {} local ...
- POJ 2456 Aggressive cows ( 二分搜索)
题目链接 Description Farmer John has built a new long barn, with N (2 <= N <= 100,000) stalls. The ...
- CSS3禁止网页中文本被选中代码
通常大家会有js来实现,另一个方案就是,将-webkit-user-select 和-moz-user-select 的值设为none,这针对于移动用户,可能会很有用.请谨慎使用这个属性:因为大部分用 ...
- css3_box-shadow使用记录
1.box-shadow这个属性有6个参数可设置,使用的时候比较少用,每次使用的时候都会忘记,故写此文作记录. 样式: /*1.添加此属性添加阴影*/ box-shadow: 0 0 10px 10p ...
- perl6中的hash定义(2)
use v6; , :b, :!c; say %ha; say %ha<a>; #这里不能用%ha{a}, {a}表示调用a()函数了, 在perl6中, {}有特别函义 say %ha{ ...
- YUV颜色编码解析(转)
原文转自 https://www.jianshu.com/p/a91502c00fb0
- Linux进程调度与源码分析(三)——do_fork()的实现原理
用户层的fork(),vfork(),clone()API函数在执行时,会触发系统调用完成从用户态陷入到内核态的过程,而上述函数的系统调用,最终实现都是通过内核函数do_fork()完成,本篇着重分析 ...
- python 学习笔记 sqlalchemy
数据库表是一个二维表,包含多行多列.把一个表的内容用Python的数据结构表示出来的话,可以用一个list表示多行,list的每一个元素是tuple,表示一行记录,比如,包含id和name的user表 ...