2018.8.9 正睿暑期集训营 Day6

时间:2.5h(实际)

期望得分:60+30+0

实际得分:40+30+0

比赛链接

这里也有一些

为什么A就是40分。。这个咋就能150+ms过呢。。http://www.zhengruioi.com/submission/26647

A 萌新拆塔(状压DP)

题目链接

如果杀掉的怪物和吃的宝石已知,那么状态也是可以直接算出来的(预处理),只需要求该状态的最大血量。

n很小,于是只需要2^n枚举已击杀的怪的状态,枚举下个怪转移DP最大血量?

因为有模仿怪,所以杀掉怪物后立即吃宝石不一定是最优的。

宝石只有在杀掉怪物后才能吃,即每个怪物有三种状态,3^n枚举就可以了。

已知状态可以算出清了哪些怪、还有哪些宝石没吃,但是可以直接用s1[s],s2[s]记录s状态清了哪些怪、吃了哪些宝石,可以直接在转移时更新(或是预处理,不过这么多次取模、除法会更慢?),枚举时也可以直接枚举里面的0(异或后lowbit枚举1)。

如果要吃某个宝石i,那么怪物i已经杀掉了,即状态s中i这一位已经是1(已经加过pw[i]),此时吃掉宝石变成2,直接再加pw[i]即可。

复杂度O(3^n*n)。

//3346ms	77996kb
#include <cstdio>
#include <cctype>
#include <cstring>
#include <algorithm>
#define lb(x) (x&-x)
#define gc() getchar()
typedef long long LL;
const int N=(1<<14)+5,M=5e6; int pw[16],bit[N],ok[16],sap[N],sdp[N],smp[N],s1[M],s2[M];
LL f[M];
struct Monster
{
int H,A,D,S,ap,dp,mp,hp;
}A[N]; inline int read()
{
int now=0;register char c=gc();
for(;!isdigit(c);c=gc());
for(;isdigit(c);now=now*10+c-'0',c=gc());
return now;
}
LL Combat(Monster mon,LL hp,int atk,int def,int mdf)
{
if(mon.S&8) mon.A=atk, mon.D=def;
if(mon.S&2) def=0;
if(atk<=mon.D) return 0ll; int dps=atk-mon.D, mon_dps=mon.A<=def?0:mon.A-def;
int tm=(mon.S&4)?2:1;
LL hpbef=hp; hp+=mdf;
if(mon.S&1) hp-=mon_dps*tm; hp-=1ll*mon_dps*tm*((mon.H+dps-1)/dps-1);
return hp>hpbef?hpbef:hp;
} int main()
{
pw[0]=1;
for(int i=1; i<=14; ++i) pw[i]=pw[i-1]*3;
for(int i=1; i<=14; ++i) bit[1<<i]=i;
for(int T=read(); T--; )
{
memset(ok,0,sizeof ok), memset(f,0,sizeof f);
int Hp=read(), Atk=read(), Def=read(), Mdf=read();
int n=read();
for(int i=0; i<n; ++i) A[i]=(Monster){read(),read(),read(),read(),read(),read(),read(),read()};
for(int K=read(); K--; ) ok[read()-1]|=1<<(read()-1); int tot=(1<<n)-1;
for(int s=0; s<=tot; ++s)
{
sap[s]=Atk, sdp[s]=Def, smp[s]=Mdf;
for(int i=0; i<n; ++i) if(s>>i&1) sap[s]+=A[i].ap, sdp[s]+=A[i].dp, smp[s]+=A[i].mp;
}
int lim=pw[n]-1; f[0]=Hp;
for(int s=0; s<lim; ++s)
{
if(!f[s]) continue;//!
int S1=s1[s], S2=s2[s];
for(int i=S1^tot,j; i; i^=lb(i))
{
j=bit[lb(i)];
if((S1&ok[j])!=ok[j]) continue;
f[s+pw[j]]=std::max(f[s+pw[j]],Combat(A[j],f[s],sap[S2],sdp[S2],smp[S2]));
s1[s+pw[j]]=S1|(1<<j), s2[s+pw[j]]=S2;
}
for(int i=S1^S2,j; i; i^=lb(i))
{
j=bit[lb(i)];
f[s+pw[j]]=std::max(f[s+pw[j]],f[s]+A[j].hp);
s1[s+pw[j]]=S1, s2[s+pw[j]]=S2|(1<<j);
}
}
printf("%lld\n",f[lim]?f[lim]:-1ll);
}
return 0;
}

B 奇迹暖暖

题目链接


C 风花雪月(DP)

题目链接

见:https://www.cnblogs.com/SovietPower/p/9862098.html。

考试代码

A

#include <cstdio>
#include <cctype>
#include <cstring>
#include <algorithm>
#define gc() getchar()
typedef long long LL;
const int N=17,M=205; int n,lim,K,Atk,Def,Mdf,dgr[N],Enum,H[N],nxt[M],to[M];
LL Hp,Ans,mx[(1<<15)+2];
struct Monster
{
int H,A,D,S,ap,dp,mp,hp;
}A[N]; inline int read()
{
int now=0;register char c=gc();
for(;!isdigit(c);c=gc());
for(;isdigit(c);now=now*10+c-'0',c=gc());
return now;
}
inline void AddEdge(int v,int u){
++dgr[v], to[++Enum]=v, nxt[Enum]=H[u], H[u]=Enum;
}
inline bool Can(int x,int s)
{
for(int i=H[x]; i; i=nxt[i]) if(!((s>>to[i]-1)&1)) return 0;
return 1;
}
inline LL Kill(Monster mon,LL hp,int atk,int def,int mdf)
{
if(mon.S>>3&1) mon.A=atk, mon.D=def;
if(mon.S>>1&1) def=0;
if(atk<=mon.D) return 0ll; int dps=atk-mon.D, mon_dps=mon.A<=def?0:mon.A-def;
int tm=(mon.S>>2&1)?2:1;
LL hpbef=hp; hp+=mdf;
if(mon.S&1) hp-=mon_dps*tm; hp-=1ll*mon_dps*tm*((mon.H+dps-1)/dps-1);
return hp>hpbef?hpbef:hp;
}
void DFS(int s,LL hp,int atk,int def,int mdf)
{
if(mx[s]>=hp) return;
if(s==lim) {mx[s]=hp, Ans=std::max(Ans,hp); return;} LL tmp=hp;
for(int i=0; i<n; ++i) if(!(s>>i&1)) tmp+=A[i+1].hp;
if(tmp<=mx[s]) return; for(int i=n; i; --i)
if(!((s>>i-1)&1) && !dgr[i] && (tmp=Kill(A[i],hp,atk,def,mdf))>0)
{
for(int j=H[i]; j; j=nxt[j]) --dgr[to[j]];
DFS(s|(1<<i-1),tmp+A[i].hp,atk+A[i].ap,def+A[i].dp,mdf+A[i].mp);
for(int j=H[i]; j; j=nxt[j]) ++dgr[to[j]];
}
} int main()
{
// freopen("A.in","r",stdin);
// freopen(".out","w",stdout); for(int T=read(); T--; )
{
Ans=-1ll, Enum=1, memset(H,0,sizeof H), memset(mx,0,sizeof mx), memset(dgr,0,sizeof dgr);
Hp=read(), Atk=read(), Def=read(), Mdf=read();
n=read(), lim=(1<<n)-1;
for(int i=1; i<=n; ++i) A[i]=(Monster){read(),read(),read(),read(),read(),read(),read(),read()};
K=read();
for(int i=1; i<=K; ++i) AddEdge(read(),read());
DFS(0,Hp,Atk,Def,Mdf);
printf("%lld\n",Ans);
}
return 0;
}

B

#include <cstdio>
#include <cctype>
#include <algorithm>
#define gc() getchar()
typedef long long LL;
const int N=101; int n,m,c;
LL Ans;
struct Event
{
int l,r,x,y;
}A[N]; inline int read()
{
int now=0;register char c=gc();
for(;!isdigit(c);c=gc());
for(;isdigit(c);now=now*10+c-'0',c=gc());
return now;
}
void DFS(int now,int rest,LL w)
{
if(!rest||now>n) {Ans=std::max(Ans,w); return;}
int X[6]; LL tmp;
for(int i=1; i<=m; ++i) X[i]=A[i].x;
DFS(now+1,rest,w);
for(int x=1; x<=rest; ++x)
{
tmp=0;
for(int i=1; i<=m; ++i)
if(A[i].l<=now&&A[i].r>=now&&A[i].x>0)
tmp+=std::min(A[i].x,x)*A[i].y, A[i].x-=x;
DFS(now+1,rest-x,w+tmp);
for(int i=1; i<=m; ++i) A[i].x=X[i];
}
}
void DFS2(int now,int rest,LL w)
{
if(!rest||now>n) {Ans=std::max(Ans,w); return;}
int X[N]; LL tmp;
for(int i=1; i<=m; ++i) X[i]=A[i].x;
DFS2(now+1,rest,w);
for(int x=1; x<=rest; ++x)
{
tmp=0;
for(int i=1; i<=m; ++i)
if(A[i].l<=now&&A[i].r>=now&&A[i].x>0)
tmp+=std::min(A[i].x,x)*A[i].y, A[i].x-=x;
DFS2(now+1,rest-x,w+tmp);
for(int i=1; i<=m; ++i) A[i].x=X[i];
}
} int main()
{
// freopen("B2.in","r",stdin);
// freopen(".out","w",stdout); n=read(), m=read(), c=read();
for(int i=1; i<=m; ++i) A[i]=(Event){read(),read(),read(),read()};
if(n<=5) DFS(1,c,0);
else DFS2(1,c,0);
printf("%lld\n",Ans); return 0;
}

C

#include <cstdio>
#include <cctype>
#include <algorithm>
#define gc() getchar()
#define INF (1e6)
#define mod (1000000007)
typedef long long LL;
const int N=12; int n,Sum,p[N],Q,c[N],have[N],Max,tot; struct Fraction
{
LL x,y;
Fraction() {x=0, y=1;}
Fraction(LL x,LL y):x(x),y(y) {} void Debug() {printf("%lld/%lld\n",x,y);}
LL Gcd(LL x,LL y) {return y?Gcd(y,x%y):x;}
inline void Fix() {LL g=Gcd(x,y); x/=g,y/=g;}
void Exgcd(LL a,LL b,LL &x,LL &y)
{
if(!b) x=1, y=0;
else Exgcd(b,a%b,y,x), y-=a/b*x;
}
void Output()
{
if(y==1) {printf("%lld\n",x); return;}
LL inv,b;
Exgcd(y,mod,inv,b);
printf("%lld\n",inv*x%mod);
}
friend bool operator <(const Fraction &f,const Fraction &g)
{
return f.x*g.y<g.x*f.y;
}
friend Fraction operator +(const Fraction &f,int num)
{
Fraction res=Fraction(f.x+f.y*num,f.y);
res.Fix();
return res;
}
friend Fraction operator +(const Fraction &f,const Fraction &g)
{
Fraction res=Fraction(f.x*g.y+g.x*f.y,f.y*g.y);
res.Fix();
return res;
}
friend Fraction operator *(const Fraction &f,int num)
{
Fraction res=Fraction(f.x*num,f.y);
res.Fix();
return res;
}
friend Fraction operator *(const Fraction &f,const Fraction &g)
{
Fraction res=Fraction(f.x*g.x,f.y*g.y);
res.Fix();
return res;
}
}Ans,f[1000003]; inline int read()
{
int now=0;register char c=gc();
for(;!isdigit(c);c=gc());
for(;isdigit(c);now=now*10+c-'0',c=gc());
return now;
}
inline LL FP(LL x,int k)
{
LL t=1;
for(; k; k>>=1, x=x*x%mod)
if(k&1) t=t*x%mod;
return t;
}
bool Check(int now,Fraction res)
{
int rest=0;
for(int i=1; i<=n; ++i)
if(have[i]>=c[i]) rest+=have[i]-c[i];
for(int i=1; i<=n; ++i)
if(have[i]<c[i])
if(rest>=4*(c[i]-have[i])) rest-=(c[i]-have[i]<<2);
else return 0;
if(rest) return 1;
putchar('\n'); Ans.Debug();puts("+=");res.Debug();
printf("Number: "); for(int i=1; i<=n; ++i) printf("%d ",have[i]); putchar('\n');putchar('\n');
Ans=Ans+res, ++tot;
return 1;
}
void DFS(int now,Fraction res)
{
// printf("now:%d ",now), res.Debug();
if(Check(now,res)||now>n) return;
int mx=(Sum-c[now])*4+c[now];
// printf("mx:%d\n",mx);
Fraction tmp=Fraction(Q,p[now]);
for(int i=0; i<=mx; ++i)
have[now]=i, printf("%d Chose %d:",now,i), (tmp*i).Debug(), DFS(now+1,std::max(tmp*i,res)), have[now]=0;
} int main()
{
freopen("C1.in","r",stdin);
// freopen(".out","w",stdout); n=read();
for(int i=1; i<=n; ++i) Q+=(p[i]=read());
for(int i=1; i<=n; ++i) Sum+=(c[i]=read());
DFS(1,Fraction(0,1));
(Ans*Fraction(1,tot)).Output(); return 0;
}

8.9 正睿暑期集训营 Day6的更多相关文章

  1. 8.9 正睿暑期集训营 Day6 C 风花雪月(DP)

    题目链接 完整比赛在这儿. 杜老师tql . 求期望要抽卡的次数,也就是求期望经历了多少不满足状态.而每个不满足的状态对答案的贡献为\(1\),所以可以直接算概率.即\(Ans=\sum_{不满足状态 ...

  2. 8.10 正睿暑期集训营 Day7

    目录 2018.8.10 正睿暑期集训营 Day7 总结 A 花园(思路) B 归来(Tarjan 拓扑) C 机场(凸函数 点分治) 考试代码 A B C 2018.8.10 正睿暑期集训营 Day ...

  3. 8.6 正睿暑期集训营 Day3

    目录 2018.8.6 正睿暑期集训营 Day3 A 亵渎(DP) B 绕口令(KMP) C 最远点(LCT) 考试代码 A B C 2018.8.6 正睿暑期集训营 Day3 时间:5h(实际) 期 ...

  4. 8.8 正睿暑期集训营 Day5

    目录 2018.8.8 正睿暑期集训营 Day5 总结 A 友谊巨轮(线段树 动态开点) B 璀璨光滑 C 构解巨树 考试代码 A B C 2018.8.8 正睿暑期集训营 Day5 时间:3.5h( ...

  5. 8.7 正睿暑期集训营 Day4

    目录 2018.8.7 正睿暑期集训营 Day4 A 世界杯(贪心) B 数组(线段树) C 淘汰赛 考试代码 A B C 2018.8.7 正睿暑期集训营 Day4 时间:5h(实际) 期望得分:. ...

  6. 8.5 正睿暑期集训营 Day2

    目录 2018.8.5 正睿暑期集训营 Day2 总结 A.占领地区(前缀和) B.配对(组合) C 导数卷积(NTT) 考试代码 T1 T2 T3 2018.8.5 正睿暑期集训营 Day2 时间: ...

  7. 8.4 正睿暑期集训营 Day1

    目录 2018.8.4 正睿暑期集训营 Day1 A 数对子 B 逆序对 C 盖房子 考试代码 A B C 2018.8.4 正睿暑期集训营 Day1 时间:4.5h(实际) 期望得分:30+50+3 ...

  8. 7.30 正睿暑期集训营 A班训练赛

    目录 2018.7.30 正睿暑期集训营 A班训练赛 T1 A.蔡老板分果子(Hash) T2 B.蔡老板送外卖(并查集 最小生成树) T3 C.蔡老板学数学(DP NTT) 考试代码 T2 T3 2 ...

  9. 正睿OI集训游记

    什么嘛....就是去被虐的... 反正就是难受就是了.各种神仙知识点,神仙题目,各式各样的仙人掌..... 但是还是学会了不少东西...... 应该是OI生涯最后一次集训了吧.... 这次的感言还是好 ...

随机推荐

  1. python---django中模板布局

    对于页面大部分一样,我们可以使用模板布局来简化 可以查看tornado中的模板引擎,基本一致 python---tornado模板引擎 对于相同代码部分,我们可以提取出来,放在布局文件layout.p ...

  2. python BeautifulSoup

    之前解析LXML,用的是XPath,现在临时被抓取写爬虫,接人家的代码,看到用的是BeautifulSoup,稍微学了下,也挺好用的,简单记录下用法,有机会做下和Xpath的对比测试 初始化 from ...

  3. Your Prediction Gets As Good As Your Data

    Your Prediction Gets As Good As Your Data May 5, 2015 by Kazem In the past, we have seen software en ...

  4. javascript设计模式开篇:Javascript 接口的实现

    javascript语言不像java. c#. c++等面向对象语言那样有完备的接口支持,在javascript中,接口的实现有三种方式,分别为注释描述.属性检查.鸭式变形.注释描述实现起来最为简单, ...

  5. es6笔记(3) 变量的解构赋值

    基本概念 本质上是一种匹配模式,只要等号两边的模式相同,那么左边的变量就可以被赋予对应的值. // 以往定义接个变量的时候,需要这样 var a = 1, b = 2, c = 3; // 使用ES6 ...

  6. HTML5 CSS Reset

    最近在学习HTML和CSS,发现一个不错的模板,放于此处. /* html5doctor.com Reset Stylesheet v1.6.1 Last Updated: 2010-09-17 Au ...

  7. 如何让你的.vue在sublime text 3 中变成彩色?

    作者:青鲤链接:https://www.zhihu.com/question/52215834/answer/129495890来源:知乎著作权归作者所有.商业转载请联系作者获得授权,非商业转载请注明 ...

  8. o(1), o(n), o(logn), o(nlogn)算法复杂度

    在描述算法复杂度时,经常用到o(1), o(n), o(logn), o(nlogn)来表示对应算法的时间复杂度, 这里进行归纳一下它们代表的含义: 这是算法的时空复杂度的表示.不仅仅用于表示时间复杂 ...

  9. Debian安装Nvidia最简单方法

    电脑配置: Dell本本 i7+gtx1050+8g 安装bumblebee: sudo apt install bumblebee-nvidia primus 以上会自动安装nvidia驱动. bu ...

  10. springcloud注解@EnableDiscoveryClient与@EnableEurekaC

    spring cloud中discovery service有许多种实现(eureka.consul.zookeeper等等),@EnableDiscoveryClient基于spring-cloud ...