BZOJ 4868-4873 题解
BZOJ4868
每个结束位置的最优值很显然具有单调性,三分,再讨论一下就好了.
#include<bits/stdc++.h>
using namespace std;
#define ll long long
#define FILE "exam"
#define up(i,j,n) for(int i=j;i<=n;i++)
#define db long double
#define pii pair<int,int>
#define pb push_back
template<class T> inline bool cmin(T& a,T b){return a>b?a=b,true:false;}
template<class T> inline bool cmax(T& a,T b){return a<b?a=b,true:false;}
template<class T> inline T squ(T a){return a*a;}
const int maxn=+,inf=1e9+,mod=;
ll read(){
ll x=,f=,ch=getchar();
while(ch<''||ch>''){if(ch=='-')f=-;ch=getchar();}
while(ch>=''&&ch<='')x=(x<<)+(x<<)+ch-'',ch=getchar();
return x*f;
}
db A,B,C;
ll a[maxn],b[maxn],d[maxn],n,m;
db check(ll s){
db ans=;
memcpy(d,b,sizeof(d));
if(A<B){
int l=,r=m;
while(l<r){
if(d[r]<s||d[l]>s)break;
if(d[r]-s>s-d[l])ans+=A*(s-d[l]),d[r]-=s-d[l],d[l]=s,l++;
else ans+=A*(d[r]-s),d[l]+=d[r]-s,d[r]=s,r--;
}
for(int i=m;i>=;i--)
if(d[i]>s)ans+=B*(d[i]-s);
for(int i=;i<=n;i++)
if(a[i]<s)ans+=C*(s-a[i]);
return ans;
}
else {
for(int i=;i<=m;i++)if(d[i]>s)ans+=B*(d[i]-s);
for(int i=;i<=n;i++)
if(a[i]<s)ans+=C*(s-a[i]);
return ans;
}
}
int main(){
freopen(FILE".in","r",stdin);
freopen(FILE".out","w",stdout);
A=read(),B=read(),C=read();
n=read(),m=read();
ll left=inf,right=-inf;
up(i,,n)a[i]=read(),cmin(left,a[i]);
up(i,,m)b[i]=read(),cmax(right,b[i]);
sort(b+,b+m+);
sort(a+,a+n+);
while(right-left>){
int mid1=(left+left+right)/;
int mid2=(left+right+right)/;
if(check(mid1)>check(mid2))left=mid1;
else right=mid2;
}
db Ans=(ll)1e18;
for(int i=left;i<=right;i++)
cmin(Ans,check(i));
printf("%.0Lf\n",Ans);
return ;
}
BZOJ4869
看到这道题后我想到了某道同样是一堆幂的神题,尽管我没写过...
正确做法是EX欧拉定理+线段树,我会欧拉定理,但我不知道什么是EX欧拉定理.
请自行百度,(尽管你baidu不到).
#include<bits/stdc++.h>
using namespace std;
#define int long long
#define FILE "verbinden"
#define up(i,j,n) for(int i=j;i<=n;++i)
#define db long double
#define pii pair<int,int>
#define pb push_back
template<class T> inline bool cmin(T& a,T b){return a>b?a=b,true:false;}
template<class T> inline bool cmax(T& a,T b){return a<b?a=b,true:false;}
template<class T> inline T squ(T a){return a*a;}
const int maxn=+,inf=1e9+;
int read(){
int x=,f=,ch=getchar();
while(ch<''||ch>''){if(ch=='-')f=-;ch=getchar();}
while(ch>=''&&ch<='')x=(x<<)+(x<<)+ch-'',ch=getchar();
return x*f;
}
int n,m,mod,C;
int a[maxn];
int op[maxn],x[maxn],y[maxn];
int fi[maxn];
int getfi(int n){
int m=sqrt(n*1.0)+,ans=;
if(n==)return ;
for(int i=;i<=m;i++){
if(n%i==)ans=ans*(i-),n/=i;
while(n%i==){
ans=ans*(i);
n/=i;
}
if(n==)break;
}
if(n!=)ans=ans*(n-);
return ans;
}
int sum[maxn],siz[maxn],ci[maxn],tot=;
void updata(int o){
sum[o]=(sum[o<<]+sum[o<<|])%mod;
siz[o]=siz[o<<]+siz[o<<|];
}
void build(int l,int r,int o){
if(l==r){
sum[o]=a[l];
siz[o]=;
return;
}
int mid=(l+r)>>;
build(l,mid,o<<);
build(mid+,r,o<<|);
updata(o);
}
bool flag=;
int qpow(int a,int b,int mod){
int ans=;
bool f0=;
while(b){
if(b&){
if(ans*a>=mod||f0)flag=;
ans=ans*a%mod;
}
if(squ(a)>=mod)f0=;
a=squ(a)%mod;
b>>=;
}
return ans;
}
int k(int a,int mod){
if(a>=mod)return a%mod+mod;
else return a;
}
void change(int l,int r,int L,int R,int o){
if(l>R||r<L)return ;
if(l==r){
if(siz[o]){
ci[l]++;
sum[o]=k(a[l],fi[ci[l]]);
for(int j=ci[l]-;j>=;j--){
flag=;
sum[o]=qpow(C,sum[o],fi[j]);
if(flag)sum[o]+=fi[j];
}
if(ci[l]==tot)siz[o]=;
}
return;
}
int mid=(l+r)>>;
if(l>=L&&r<=R){
if(siz[o<<])change(l,mid,L,R,o<<);
if(siz[o<<|])change(mid+,r,L,R,o<<|);
updata(o);
return;
}
change(l,mid,L,R,o<<);
change(mid+,r,L,R,o<<|);
updata(o);
}
int query(int l,int r,int L,int R,int o){
if(l>R||r<L)return ;
if(l>=L&&r<=R)return sum[o];
int mid=(l+r)>>;
return (query(l,mid,L,R,o<<)+query(mid+,r,L,R,o<<|))%mod;
}
main(){
freopen(FILE".in","r",stdin);
freopen(FILE".out","w",stdout);
n=read(),m=read(),mod=read(),C=read();
up(i,,n)a[i]=read();
up(i,,m)op[i]=read(),x[i]=read(),y[i]=read();
build(,n,);
fi[]=mod;
for(int i=;i<=m;i++){
fi[i]=getfi(fi[i-]);
if(fi[i]==){
fi[i+]=;
tot=i+;
break;
}
}
up(i,,m){
if(op[i]==)change(,n,x[i],y[i],);
if(op[i]==)printf("%d\n",query(,n,x[i],y[i],));
}
return ;
}
BZOJ4870
搞出DP方程,然后DP快速幂,或者矩阵快速幂任你挑.(这题可以搞NTT优化).
#include<bits/stdc++.h>
using namespace std;
#define ll long long
#define FILE "problem"
#define up(i,j,n) for(int i=j;i<=n;i++)
#define db long double
#define pii pair<int,int>
#define pb push_back
template<class T> inline bool cmin(T& a,T b){return a>b?a=b,true:false;}
template<class T> inline bool cmax(T& a,T b){return a<b?a=b,true:false;}
template<class T> inline T squ(T a){return a*a;}
const int maxn=+,inf=1e9+;
int read(){
int x=,f=,ch=getchar();
while(ch<''||ch>''){if(ch=='-')f=-;ch=getchar();}
while(ch>=''&&ch<='')x=(x<<)+(x<<)+ch-'',ch=getchar();
return x*f;
}
ll mod,n,K,r;
void getmod(ll& a){if(a>mod)a-=mod;}
struct Matrix{
ll num[][];
Matrix(){memset(num,,sizeof(num));}
Matrix(ll a){
memset(num,,sizeof(num));
for(int i=;i<K;i++)
num[i][i]=a;
}
Matrix operator*(const Matrix& b){
Matrix c;
for(int i=;i<K;i++)
for(int j=;j<K;j++)
for(int k=;k<K;k++)
getmod(c.num[i][j]+=num[i][k]*b.num[k][j]%mod);
return c;
}
}b,a; int main(){
freopen(FILE".in","r",stdin);
freopen(FILE".out","w",stdout);
n=read(),mod=read(),K=read(),r=read();
for(int i=;i<K;i++)
b.num[i][(i+)%K]++,b.num[i][i]++;
Matrix ans();
n=n*K;
while(n){
if(n&)ans=ans*b;
b=b*b;
n>>=;
}
printf("%lld\n",ans.num[][r]);
return ;
}
BZOJ 4871
一道状态有些复杂的树形DP.
状态自行baidu.
注:此方法已被HACK,请自行找不会被卡的方法.
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
#define ll long long
#define FILE "treediagram"
#define up(i,j,n) for(int i=j;i<=n;i++)
#define db long double
#define pii pair<int,int>
#define pb push_back
#define mem(a,L) memset(a,0,sizeof(int)*(L+1))
template<class T> inline bool cmin(T& a,T b){return a>b?a=b,true:false;}
template<class T> inline bool cmax(T& a,T b){return a<b?a=b,true:false;}
template<class T> inline T squ(T a){return a*a;}
const int maxn=+,inf=1e9+,mod=;
int read(){
int x=,f=,ch=getchar();
while(ch<''||ch>''){if(ch=='-')f=-;ch=getchar();}
while(ch>=''&&ch<='')x=(x<<)+(x<<)+ch-'',ch=getchar();
return x*f;
}
struct node{
int x,y,next;
}e[maxn];
int len,linkk[maxn],T,ch,p0,h0,p1,h1,n;
int vis[maxn],de[maxn],h[maxn],f[maxn],g[maxn],d[maxn];
void insert(int x,int y){e[++len].y=y;e[len].x=x;e[len].next=linkk[x];linkk[x]=len;}
struct Node{
int a,b;
Node(){a=b=;}
};
void dp(int p){
if(vis[p])return;vis[p]=;
int x=e[p].y,child=;
Node t;
for(int i=linkk[x];i;i=e[i].next) if(i!=(p^)){
child++;
dp(i);
cmax(d[p],d[i]);
if(f[i]>=t.a)t.b=t.a,t.a=f[i];
else if(f[i]>t.b)t.b=f[i];
}
f[p]=max(t.a,)+child-;
g[p]=max(t.a,)+max(t.b,)+child-;
cmax(d[p],g[p]);
}
int a[],b[];
bool cmp(const int& a,const int& b){return a>b;}
void solve(){
int ans=;
for(int i=;i<=len;i++)dp(i),dp(i^),cmax(ans,d[i]+d[i^]);
for(int x=;x<=n;x++){
memset(a,,sizeof(a));
memset(b,,sizeof(b));
for(int i=linkk[x];i;i=e[i].next){
a[]=f[i];sort(a,a+,cmp);
b[]=d[i];sort(b,b+,cmp);
}
cmax(ans,b[]+b[]+);
cmax(ans,a[]+a[]+a[]+de[x]-);
cmax(ans,a[]+a[]+a[]+a[]+de[x]-);
}
printf("%d\n",ans);
}
int main(){
freopen(FILE".in","r",stdin);
freopen(FILE".out","w",stdout);
int T=read(),ch=read();
while(T--){
n=read();
if(ch)p0=read(),p1=read();
if(ch>)h0=read(),h1=read();
if(n==){puts("");continue;}
len=;mem(linkk,n);mem(de,n);
up(i,,n){int x=read(),y=read();insert(x,y);insert(y,x);de[x]++,de[y]++;}
up(i,,len)vis[i]=,f[i]=g[i]=d[i]=;
solve();
}
return ;
}
BZOJ 4872
概率DP.
给个我能理解的讲解的链接:http://www.cnblogs.com/GXZlegend/p/6764969.html
#include<bits/stdc++.h>
using namespace std;
#define ll long long
#define FILE "trennen"
#define up(i,j,n) for(ll i=j;i<=n;i++)
#define db long double
#define pii pair<ll,ll>
#define pb push_back
template<class T> inline bool cmin(T& a,T b){return a>b?a=b,true:false;}
template<class T> inline bool cmax(T& a,T b){return a<b?a=b,true:false;}
template<class T> inline T squ(T a){return a*a;}
const ll maxn=+,inf=1e9+,mod=;
ll read(){
ll x=,f=,ch=getchar();
while(ch<''||ch>''){if(ch=='-')f=-;ch=getchar();}
while(ch>=''&&ch<='')x=(x<<)+(x<<)+ch-'',ch=getchar();
return x*f;
}
ll n,k;
ll a[maxn],ans=;
ll fac[maxn];
ll qpow(ll a,ll b){
ll ans=;
while(b){
if(b&)ans=ans*a%mod;
a=squ(a)%mod;
b>>=;
}
return ans;
}
ll vis[maxn];
int main(){
freopen(FILE".in","r",stdin);
freopen(FILE".out","w",stdout);
n=read(),k=read();
up(i,,n)a[i]=read();
for(ll i=n;i>=;i--){
ll x=a[i];
for(ll j=;j*i<=n;j++)
x^=vis[j*i];
if(x)ans++,vis[i]=;
}
fac[]=;for(ll i=;i<=n;i++)fac[i]=fac[i-]*i%mod;
printf("%lld\n",(ll)ans*fac[n]%mod);
return ;
}
BZOJ 4873
最简单的那种最大权闭合子图.
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
#define ll long long
#define FILE "sushi"
#define up(i,j,n) for(int i=j;i<=n;i++)
#define db long double
#define pii pair<int,int>
#define pb push_back
template<class T> inline bool cmin(T& a,T b){return a>b?a=b,true:false;}
template<class T> inline bool cmax(T& a,T b){return a<b?a=b,true:false;}
template<class T> inline T squ(T a){return a*a;}
const int maxn=+,inf=1e8+,mod=;
int read(){
int x=,f=,ch=getchar();
while(ch<''||ch>''){if(ch=='-')f=-;ch=getchar();}
while(ch>=''&&ch<='')x=(x<<)+(x<<)+ch-'',ch=getchar();
return x*f;
}
int S,T,n,m,cnt;
struct node{
int y,next,flow,rev;
node(int y=,int next=,int flow=,int rev=):y(y),next(next),flow(flow),rev(rev){}
}e[maxn];int len,linkk[maxn];
int v[][];
void insert(int x,int y,int flow){
e[++len].y=y;e[len].next=linkk[x];linkk[x]=len;e[len].flow=flow;e[len].rev=len+;
e[++len].y=x;e[len].next=linkk[y];linkk[y]=len;e[len].flow=;e[len].rev=len-;
}
int q[maxn],d[maxn],head,tail;
bool makelevel(){
memset(d,-,sizeof(int)*(cnt+));
d[S]=;head=tail=;q[++tail]=S;
while(++head<=tail){
int x=q[head];
for(int i=linkk[x];i;i=e[i].next){
int y=e[i].y;
if(d[y]==-&&e[i].flow)
q[++tail]=y,d[y]=d[x]+;
}
}
return d[T]!=-;
}
int makeflow(int x,int flow){
if(x==T||!flow)return flow;
int maxflow=,dis=;
for(int i=linkk[x];i&&maxflow<flow;i=e[i].next){
int y=e[i].y;
if(d[y]==d[x]+&&e[i].flow)
if(dis=makeflow(y,min(flow-maxflow,e[i].flow))){
e[i].flow-=dis;
e[e[i].rev].flow+=dis;
maxflow+=dis;
}
}
if(!maxflow)d[x]=-;
return maxflow;
}
int dinic(){
int ans=,d;
while(makelevel())
while(d=makeflow(S,inf))
ans+=d;
return ans;
}
int ID1[][],ID2[maxn],a[maxn];
int main(){
freopen(FILE".in","r",stdin);
freopen(FILE".out","w",stdout);
n=read();m=read();
up(i,,n)a[i]=read();
up(i,,n)up(j,i,n){
v[i][j]=read();if(i==j)v[i][j]-=a[i];
ID1[i][j]=++cnt;
}
up(i,,n)up(j,i,n)if(i!=j)insert(ID1[i][j],ID1[i][j-],inf),insert(ID1[i][j],ID1[i+][j],inf);
S=++cnt,T=++cnt;
if(m==)up(i,,n){
if(!ID2[a[i]]){
ID2[a[i]]=++cnt;
insert(ID2[a[i]],T,squ(a[i]));
}
insert(ID1[i][i],ID2[a[i]],inf);
}
int Sum=;
up(i,,n)up(j,i,n){
if(v[i][j]>)insert(S,ID1[i][j],v[i][j]),Sum+=v[i][j];
else if(v[i][j]<)insert(ID1[i][j],T,-v[i][j]);
}
int ans=dinic();
printf("%d\n",Sum-ans);
return ;
}
我们用这套题考了两天.
我的考试结果并不是很理想.
考完发现全是傻逼题.
发现了两点很不好的地方是:
1.考试时不敢想正解.(出题人语文水平高超)
2.很容易被前面的引导.(容易被出题人引导)
考试时题面的长度不一定与难度成反比.
很多题目打暴力的难度比打正解大.
因为正解的模型我可能建过很多次,但暴力的模型我第一次建.
但有些时候打暴力比打正解划算,因为你不会正解...
所以说了这么多,你需要做的是:
考试时摆脱前面题目不会的心理负担,全力分析这道题,争取AC,当然不能AC就只能暴力了.
蛤蛤,其实我说了一堆废话.
BZOJ 4868-4873 题解的更多相关文章
- BZOJ 1179 Atm 题解
BZOJ 1179 Atm 题解 SPFA Algorithm Tarjan Algorithm Description Input 第一行包含两个整数N.M.N表示路口的个数,M表示道路条数.接下来 ...
- 【题解】期末考试 六省联考 2017 洛谷 P3745 BZOJ 4868 贪心 三分
题目传送门:这里是萌萌哒传送门(>,<) 啊♀,据说这题有个完全贪心的做法,但是要维护太多东西好麻烦的(>,<),于是就来口胡一发三分的做法. 思路很简单,假设我指定了一个x, ...
- 【BZOJ】4873: [Shoi2017]寿司餐厅
[题目]#2146. 「SHOI2017」寿司餐厅 [题意]给定n种寿司的代号,取区间[i,j]的寿司收益是d[i,j]和所有子区间的d,吃了c(c>0)种代号x的寿司的代价是mx^2+cx,给 ...
- BZOJ 4236~4247 题解
BZOJ 4236 JOIOJI f[i][0..2]表示前i个字符中′J′/′O′/′I′的个数 将二元组<f[i][0]−f[i][1],f[i][1]−f[i][2]>扔进map,记 ...
- Bzoj 2064 分裂 题解
2064: 分裂 Time Limit: 10 Sec Memory Limit: 64 MBSubmit: 570 Solved: 350[Submit][Status][Discuss] De ...
- BZOJ 4472 salesman 题解
题目 某售货员小T要到若干城镇去推销商品,由于该地区是交通不便的山区,任意两个城镇之间都只有唯一的可能经过其它城镇的路线.小T可以准确地估计出在每个城镇停留的净收益.这些净收益可能是负数,即推销商品的 ...
- bzoj 4868: [Shoi2017]期末考试
Description 有n位同学,每位同学都参加了全部的m门课程的期末考试,都在焦急的等待成绩的公布.第i位同学希望在第ti天 或之前得知所.有.课程的成绩.如果在第ti天,有至少一门课程的成绩没有 ...
- BZOJ 4868 [Shoi2017]期末考试 ——三分 枚举
考场上xjb三分过掉了. 然后$sdfzyhx$.$silvernebula$ $O(n)$虐掉了. 我还是太菜了 #include <cstdio> #include <cmath ...
- Bzoj 2288 生日礼物题解
2288: [POJ Challenge]生日礼物 Time Limit: 10 Sec Memory Limit: 128 MBSubmit: 856 Solved: 260[Submit][S ...
- [CQOI2007]涂色paint(BZOJ 1260)题解
题目描述 假设你有一条长度为5的木版,初始时没有涂过任何颜色.你希望把它的5个单位长度分别涂上红.绿.蓝.绿.红色,用一个长度为5的字符串表示这个目标:RGBGR. 每次你可以把一段连续的木版涂成一个 ...
随机推荐
- GridView.setChoiceMode(GridView.CHOICE_MODE_MULTIPLE_MODAL)不兼容低版本号系统解决方式
项目开发中须要使用GridView批处理操作,多项选择. 可是GridView.setChoiceMode(GridView.CHOICE_MODE_MULTIPLE_MODAL)不兼容低版本号. 找 ...
- OSG(OpenSceneGraphic) 渲染引擎架构--整体认识 [转]
原文:http://blog.csdn.net/zangle260/article/details/41123067?utm_source=tuicool 本文参考<<osg最长一帧> ...
- Mysql中delimiter作用
1. delimiter delimiter是mysql分隔符.在mysqlclient中分隔符默认是分号(:). 假设一次输入的语句较多,而且语句中间有分号,这时须要新指定一个特殊的分隔符. 2. ...
- FreeMark的list应用
语法:<#if></#if>后台传送List,前台html页面中获取该list并显示: <#if userList?exists> <#list userLi ...
- spring中的异步事件
这里讲解一下Spring对异步事件机制的支持,实现方式有两种: 1.全局异步 即只要是触发事件都是以异步执行,具体配置(spring-config-register.xml)如下: Java代码 ...
- Spring Boot 从入门到实战汇总
之前写过几篇spring boot入门到实战的博文,因为某些原因没能继续. 框架更新迭代很快,之前还是基于1.x,现在2.x都出来很久了.还是希望能从基于该框架项目开发的整体有一个比较系统的梳理,于是 ...
- items" does not support runtime expression
<%@taglib prefix="c" uri="http://java.sun.com/jstl/core"%> 更改为 <%@tagl ...
- android利用apkplug框架实现主应用与插件通讯(传递随意对象)实现UI替换
时光匆匆,乍一看已半年过去了,经过这半年的埋头苦干今天最终有满血复活了. 利用apkplug框架实现动态替换宿主Activity中的UI元素.以达到不用更新应用就能够更换UI样式的目的. 先看效果图: ...
- hadoop权威指南学习
通常情况下,处理少量的大型文件更容易.更有效,为什么呢? map阶段中的键如果不需要可以忽略掉? MapReduce过程也可以用于本地文件的处理,但是如果是要使用到集群的话还需要HDFS. Data ...
- window下Opengl与vs2012环境配置
一.opengl与C++环境配置 1. 下载opengl包. 2. 将压缩包解压后, (1)将.dll文件(GLU.DLL, GLUT.DLL, GLUT32.DLL)放到C:\Windows\Sys ...