Codeforces Round #263 (Div. 1)-A,B,C
A:
这道题目还是非常easy的,做过非常多遍了。相似于分割木板的问题。
把全部的数放在一个优先队列里,弹出两个最大的,然后合并,把结果放进去。依次进行。
#include <iostream>
#include<stdio.h>
#include<stdlib.h>
#include<time.h>
#include<vector>
#include<algorithm>
#include<string.h>
#include<queue>
using namespace std;
#define LL __int64
#define INF 1000000000
LL a[330000];
priority_queue<LL>que;
int main()
{
int n;
while(~scanf("%d",&n))
{
LL sum=0;
while(!que.empty())que.pop();
for(int i=1;i<=n;i++)
{
scanf("%I64d",&a[i]);
sum+=a[i];
que.push(a[i]);
}
LL ans=0;
while(!que.empty())
{
LL x=que.top();
que.pop();
if(!que.empty())
{
LL y=que.top();
que.pop();
ans+=x;
ans+=y;
que.push(x+y);
}
else
{
ans+=x;
break;
}
}
cout<<ans<<endl;
}
return 0;
}
B:树形DP
dp[i][0]:以i节点为根的子树对上面的贡献为0时的情况数
dp[i][1]:以i节点为根的子树对上面的贡献为1时的情况数
假设i节点为0
非常明显对于dp[i][1]:
枚举哪颗子树对i贡献了1,假如a,b,c为i的子树,则
dp[i][1]=dp[a][1]*dp[b][0]*dp[c][0]+dp[a][0]*dp[b][1]*dp[c][0]+dp[a][0]*dp[b][0]*dp[c][1];
对于dp[i][0]:
1,假设全部的子树都没有对i贡献
dp[i][0]+=dp[a][0]*dp[b][0]*dp[c][0];
2,存在一个子树对i贡献了1,可是i节点上方的边被切掉
dp[i][0]+=dp[i][1];
假设i节点为1
dp[i][0]=dp[i][1]=dp[a][0]*dp[b][0]*dp[c][0];
#include<iostream>
#include<stdio.h>
#include<string.h>
#include<algorithm>
#include<iostream>
#include<vector>
#include<set>
#include<string>
using namespace std;
#define maxn 110000
#define LL __int64
#define mod 1000000007
vector<int>old[maxn];
vector<int>now[maxn];
int vis[maxn];
void change(int x)
{
int i;
vis[x]=1;
for(i=0; i<old[x].size(); i++)
{
if(vis[old[x][i]])continue;
now[x].push_back(old[x][i]);
change(old[x][i]);
}
}
LL dp[maxn][2];
int a[maxn];
LL q_mod(LL a,LL b,LL n)
{
LL ret=1;
LL tmp=a;
while(b)
{
//基数存在
if(b&0x1) ret=ret*tmp%n;
tmp=tmp*tmp%n;
b>>=1;
}
return ret;
}
LL dos(LL x,LL y,LL z)
{ x=x*z;
x=x%mod;
x=x*q_mod(y,mod-2,mod);
x=x%mod;
return x;
}
void dfs(int x)
{
int leap=0;
LL sum=1;
for(int i=0; i<now[x].size(); i++)
{
dfs(now[x][i]);
leap=1;
sum=sum*dp[now[x][i]][0];
sum=sum%mod;
}
if(leap==0)
{
if(a[x]==0)
{
dp[x][0]=1;
dp[x][1]=0;
}
else
{
dp[x][1]=1;
dp[x][0]=1;
}
// cout<<x<<" "<<dp[x][1]<<" "<<dp[x][0]<<endl;
return ;
}
if(a[x]==0)
{
dp[x][0]=sum;
dp[x][1]=0;
for(int i=0; i<now[x].size(); i++)
{
int y=now[x][i];
dp[x][1]+=dos(sum,dp[y][0],dp[y][1]);
dp[x][1]%=mod;
}
dp[x][0]+=dp[x][1];
dp[x][0]%=mod;
}
else
{
dp[x][1]=sum;
dp[x][0]=sum;
}
// cout<<x<<" "<<dp[x][1]<<" "<<dp[x][0]<<endl;
}
int main()
{
int i,n,j;
int aa,ab;
while(~scanf("%d",&n))
{
memset(vis,0,sizeof(vis));
for(i=0; i<=n; i++)
{
old[i].clear();
now[i].clear();
}
for(i=1; i<n; i++)
{
scanf("%d",&aa);
aa=aa+1;
ab=i+1;
// cout<<" "<<aa<<" -" <<ab<<endl;
old[aa].push_back(ab);
old[ab].push_back(aa);
}
for(int i=1; i<=n; i++)scanf("%d",&a[i]);
change(1);
dfs(1);
cout<<dp[1][1]<<endl;
}
return 0;
}
C:
非常明显,假设翻转大于一半,相当于先旋转。然后翻转剩下的。
那么我们最多会翻转2*n个数字。
然后就暴力枚举当前的状态。
然后用线段树储存每一个节点有多少长度,然后询问的时候区间求和。
#include<iostream>
#include<stdio.h>
#include<string.h>
#include<algorithm>
#include<iostream>
#include<vector>
#include<set>
#include<string>
using namespace std;
#define maxn 110000
#define LL __int64
#define mod 1000000007
#define mem(a,b) (memset(a),b,sizeof(a))
#define lmin 1
#define rmax n
#define lson l,(l+r)/2,rt<<1
#define rson (l+r)/2+1,r,rt<<1|1
#define root lmin,rmax,1
#define now l,r,rt
#define int_now int l,int r,int rt
int have[maxn];
int sum[maxn<<2];
void creat(int_now)
{
if(l!=r)
{
creat(lson);
creat(rson);
sum[rt]=sum[rt<<1]+sum[rt<<1|1];
}
else
{
sum[rt]=1;
}
}
void updata(int ll,int x,int_now)
{
if(ll>r||ll<l)return;
if(ll==l&&l==r)
{
sum[rt]=x;
return ;
}
updata(ll,x,lson);
updata(ll,x,rson);
sum[rt]=sum[rt<<1]+sum[rt<<1|1];
}
int query(int ll,int rr,int_now)
{
if(ll>r||rr<l)return 0;
if(ll<=l&&rr>=r)return sum[rt];
return query(ll,rr,lson)+query(ll,rr,rson);
}
int leap,st,ed,n;
void chu(int p)
{
if(leap==0)
{
st=st+p;
ed=ed;
for(int i=p; i>=1; i--)
{
have[st+i-1]=have[st+i-1]+have[st-i];
updata(st+i-1,have[st+i-1],root);
}
}
else
{
ed=ed-p;
st=st;
for(int i=p; i>=1; i--)
{
have[ed-i+1]=have[ed-i+1]+have[ed+i];
updata(ed-i+1,have[ed-i+1],root);
}
}
}
int main()
{
int q;
while(~scanf("%d%d",&n,&q))
{
creat(root);
for(int i=1; i<=n; i++)have[i]=1;
int len=n;
leap=0;
st=1;
ed=n;
int a,b,p,t;
while(q--)
{
scanf("%d",&t);
if(t==1)
{
scanf("%d",&p);
len=ed-st+1;
int ban=len/2;
if(p<=ban)
{
chu(p);
}
else
{
len=ed-st+1;
p=len-p;
leap=leap^1;
chu(p);
}
}
else
{
scanf("%d%d",&a,&b);
if(leap==0)
{
a=a+st;
b=b+st-1;
}
else
{
a=ed-a;
b=ed-b+1;
swap(a,b);
}
if(a>ed||b<st)
{
cout<<"0"<<endl;
continue;
}
if(b>ed)b=ed;
if(a<st)a=st;
cout<<query(a,b,root)<<endl;
}
}
}
return 0;
}
Codeforces Round #263 (Div. 1)-A,B,C的更多相关文章
- 贪心 Codeforces Round #263 (Div. 2) C. Appleman and Toastman
题目传送门 /* 贪心:每次把一个丢掉,选择最小的.累加求和,重复n-1次 */ /************************************************ Author :R ...
- Codeforces Round #263 (Div. 2)
吐槽:一辈子要在DIV 2混了. A,B,C都是简单题,看AC人数就知道了. A:如果我们定义数组为N*N的话就不用考虑边界了 #include<iostream> #include &l ...
- Codeforces Round #263 (Div. 1)
B 树形dp 组合的思想. Z队长的思路. dp[i][1]表示以i为跟结点的子树向上贡献1个的方案,dp[i][0]表示以i为跟结点的子树向上贡献0个的方案. 如果当前为叶子节点,dp[i][0] ...
- Codeforces Round #263 Div.1 B Appleman and Tree --树形DP【转】
题意:给了一棵树以及每个节点的颜色,1代表黑,0代表白,求将这棵树拆成k棵树,使得每棵树恰好有一个黑色节点的方法数 解法:树形DP问题.定义: dp[u][0]表示以u为根的子树对父亲的贡献为0 dp ...
- Codeforces Round #263 (Div. 2) D. Appleman and Tree(树形DP)
题目链接 D. Appleman and Tree time limit per test :2 seconds memory limit per test: 256 megabytes input ...
- Codeforces Round #263 (Div. 2) A B C
题目链接 A. Appleman and Easy Task time limit per test:2 secondsmemory limit per test:256 megabytesinput ...
- Codeforces Round #263 (Div. 1) C. Appleman and a Sheet of Paper 树状数组暴力更新
C. Appleman and a Sheet of Paper Appleman has a very big sheet of paper. This sheet has a form of ...
- Codeforces Round #263 (Div. 2) proC
题目: C. Appleman and Toastman time limit per test 2 seconds memory limit per test 256 megabytes input ...
- Codeforces Round #263 (Div. 2)C(贪心,联想到huffman算法)
数学家伯利亚在<怎样解题>里说过的解题步骤第二步就是迅速想到与该题有关的原型题.(积累的重要性!) 对于这道题,可以发现其实和huffman算法的思想很相似(可能出题人就是照着改编的).当 ...
- Codeforces Round #263 (Div. 2) proB
题目: B. Appleman and Card Game time limit per test 1 second memory limit per test 256 megabytes input ...
随机推荐
- JavaScript设计模式 (1) 原型模式
原型模式(Prototype):用原型实例指向创建类对象,使用于创建新对象的类共享原型对象的属性以及方法. //图片轮播类 var LoopImages = function (imgArr, con ...
- Shell script之How to write
Write shell script: 1) Editor like vi or mcedi 2) Set execute permission for your script chmod perm ...
- 用PHP开发自己的独立博客(一)——概述
开篇废话:因为重新回归朝九晚五的生活,于是就想开始写技术博客,当是做技术文档了.于是试用了各类博客,CSDN.cnblogs都还不错.简单试用了一下,说说各自的特点. CSDN的界面不能定制,使用默认 ...
- GAN生成图像论文总结
GAN Theory Modifyingthe Optimization of GAN 题目 内容 GAN DCGAN WGAN Least-square GAN Loss Sensi ...
- FileInputStream实现读取文件内容并输出到屏幕上
java输入输出流是站在程序的角度来说的.从文件中读取数据用输入流,向文件中写数据用输出流. package com.janson.day20180827; import java.io.FileIn ...
- python3.x Day2 购物车程序练习
购物车程序: 1.启动程序后,输入用户名密码后,如果是第一次登录,让用户输入工资,然后打印商品列表 2.允许用户根据商品编号购买商品 3.用户选择商品后,检测余额是否够,够就直接扣款,不够就提醒 4. ...
- java--删除链表偶数节点
public class ListNode { int data;//当前节点的值 ListNode next = null;//是指向下一个节点的指针/引用 public ListNode(int ...
- elasticsearch数据库使用
elasticsearch的一个最为显著的优点:快速全文检索.关于elasticsearch 全文检索的原理,请看:https://blog.csdn.net/wolfcode_cn/article/ ...
- xe的debug怪现象
死活有问题,而且不能重新编译生成文件. 查网上说明:在删除项目xxx.dproj文件后,然后打开dpk文件,会自动生成.dproj文件,再然后一切OK. 的确如此,但莫名其妙.
- https://gitee.com/tomsun28/bootshiro-------需要研究的项目
https://gitee.com/tomsun28/bootshiro-------需要研究的项目