输入格式

第一行为三个整数n,m,K,分别表示地图的长和宽,以及最多能放置的炮塔数量。 
接下来的n行,每行包含m个字符,‘#’表示地图上原有的障碍,‘.’表示该处为空地,
数据保证在原地图上存在S到T的路径。


输出格式

输出在合理布阵下,喵星人采取最优策略后,会受到的最大伤害。 
注意必须保证在布阵结束后喵星人仍然可以沿一条或以上的路径从起点S到达终点T,
否则他们组织更大规模的侵略。


提示

【数据范围】 
对于30%的数据,保证:
1<=N,M<=6
对于100%的数据,保证:
1<=N<=6,1<=M<=20,1<=K<=15,且从S到T的路径必定存在。


  • 题解:

    • 由于可以无限放置障碍,所以最后一定只会有一条路径;
    • 插头$dp$求出路径即可;
    • 注意和普通路径不同,路径不能组成四连通块;
 #include<bits/stdc++.h>
#define il inline
#define rg register
using namespace std;
const int N=,M=,sz=1e5;
int n,m,K,c1[N],c2[N],cur,ans;
char s[M][M];
struct HASH{
int o,hd[sz],v[sz],w[sz],nt[sz];
il void init(){for(int i=;i<=o;++i)hd[v[i]%sz]=,v[i]=w[i]=nt[i]=;o=;}
il void upd(int x,int y){
for(rg int i=hd[x%sz];i;i=nt[i])if(v[i]==x){
if(w[i]<y)w[i]=y;
return;
}
nt[++o]=hd[x%sz],hd[x%sz]=o,v[o]=x,w[o]=y;
}
}f[][M];
il void upd(int&x,int y){if(x<y)x=y;}
il void decode(int x){
for(rg int i=;i<=m;++i)c1[i]=x&,x>>=;
for(rg int i=;i<=m;++i)c2[i]=x&,x>>=;
}
il int encode(){
int x=;
for(rg int i=m;~i;--i)x=(x<<)^c2[i];
for(rg int i=m;~i;--i)x=(x<<)^c1[i];
return x;
}
il int le(int x){
for(rg int i=x,y=;~i;--i)if(c1[i]&&c1[i]!=){
y+=(c1[i]&)?:-;
if(!y)return i;
}return ;
}
il int ri(int x){
for(rg int i=x,y=;i<=m;++i)if(c1[i]&&c1[i]!=){
y+=(c1[i]&)?:-;
if(!y)return i;
}return ;
}
il int cal1(int x){
int l=max(x-,),r=min(x+,m),re=;
for(rg int i=l;i<=r;++i)if(c2[i]==)re++;
return re;
}
il int cal2(int x){
int l=max(x-,),r=min(x+,m),re=;
for(rg int i=l;i<=r;++i)if(c2[i]==)re++;
return re;
}
il bool check(int j){
for(rg int i=;i<=m;++i)if(i!=j&&i!=j+&&c1[i])return false;
return true;
}
int main(){
#ifndef ONLINE_JUDGE
freopen("C.in","r",stdin);
freopen("C.out","w",stdout);
#endif
scanf("%d%d%d",&n,&m,&K);
for(rg int i=;i<n;++i)scanf("%s",s[i]);
if(n<m){
for(rg int i=;i<n;++i)
for(rg int j=i+;j<m;++j){
swap(s[i][j],s[j][i]);
}
swap(n,m);
}
f[cur=][].upd(,);
for(rg int i=;i<n;++i)
for(rg int j=;j<m;++j){
for(rg int k=;k<=K;++k){
for(rg int l=;l<=f[cur][k].o;++l){
int w=f[cur][k].w[l];
decode(f[cur][k].v[l]);
if(!j){
if(c1[m])continue;
for(rg int i=m;i;--i)c1[i]=c1[i-],c2[i]=c2[i-];
c1[]=c2[]=;
}
/*
{
printf("%d %d %d:\n",i,j,k);
for(int i=0;i<=m;++i)printf("%d ",c1[i]);
puts("");
for(int i=0;i<=m;++i)printf("%d ",c2[i]);
puts("");
printf("%d\n",w);
printf("#\n");
}*/ int &p=c1[j],&q=c1[j+],&r=c2[j],w1=w+cal1(j),w2=w+cal2(j);
int t1=j&&(c2[j-]&),t2=j!=m&&(c2[j+]&);
if(s[i][j]=='#'){
if(p||q)continue;
r=,f[cur^][k].upd(encode(),w);
}else if(!p&&!q){
if(s[i][j]=='.'){
p=,q=;
r=,f[cur^][k].upd(encode(),w);
if(k<K)r=,f[cur^][k+].upd(encode(),w1);
}
if(t1||t2)continue;
if(s[i][j]=='S'||s[i][j]=='T'){
p=,q=,r=,f[cur^][k].upd(encode(),w2);
p=,q=,r=,f[cur^][k].upd(encode(),w2);
}else p=,q=,r=,f[cur^][k].upd(encode(),w2);
}else if(!p||!q){
if(t1&&t2)continue;
if(s[i][j]=='S'||s[i][j]=='T'){
if(p+q!=){
if(p+q==)c1[ri(j)]=;else c1[le(j+)]=;
p=q=,r=,f[cur^][k].upd(encode(),w2);
}
else if(check(j))p=,q=,r=,f[cur^][k].upd(encode(),w2);
}else{
r=,swap(p,q),f[cur^][k].upd(encode(),w2);
r=,swap(p,q),f[cur^][k].upd(encode(),w2);
}
}else{
if(p==&&q==){
p=q=,r=,f[cur^][k].upd(encode(),w2);
}else if(p==||q==){
if(p+q-==)c1[ri(j)]=;
else if(p+q-==)c1[le(j+)]=;
p=q=,r=,f[cur^][k].upd(encode(),w2);
}else {
if(p==&&q==)continue;
if(p==q){
if(p==)c1[ri(j+)]=;
else c1[le(j)]=;
}
p=q=,r=,f[cur^][k].upd(encode(),w2);
}
}
}
f[cur][k].init();
}
cur^=;
}
for(int i=;i<=K;++i)
for(int j=;j<=f[cur][i].o;++j){
decode(f[cur][i].v[j]);
if(check(m+))upd(ans,f[cur][i].w[j]);
}
printf("%d\n",ans);
return ;
}

bzoj2755【SCOI2012】喵星人的入侵的更多相关文章

  1. 洛谷 P2337 【[SCOI2012]喵星人的入侵】

    这几天一直在刷插头Dp,写了几道入门题后,觉得还比较水,直到我发现了这一题.... 题目大意:给你一个n*m的地图,有些是空地,有些是障碍,还有两个是ST,在给你一个L,代表可以放L个炮台,你要在空地 ...

  2. 插头dp小结

    插头dp: \(A:\)插头dp是什么? \(B:\)一种基于连通性状态压缩的动态规划问题 \(A:\)请问有什么应用呢? \(B:\)各种网格覆盖问题,范围允许状压解决,常用于计算方案数与联通块权值 ...

  3. bzoj AC倒序

    Search GO 说明:输入题号直接进入相应题目,如需搜索含数字的题目,请在关键词前加单引号 Problem ID Title Source AC Submit Y 1000 A+B Problem ...

  4. BZOJ_2754__[SCOI2012]_喵星球上的点名_(暴力+后缀数组)

    描述 http://www.lydsy.com/JudgeOnline/problem.php?id=2754 给出n个姓名串和m个点名串.求每个点名串在多少人的姓名中出现过(在名中出现或在姓中出现, ...

  5. BZOJ 2754([SCOI2012]喵喵叫的星球-统计序列的后缀阵列中子序列出现次数)

    2754: [SCOI2012]喵喵叫的星球 Time Limit: 20 Sec  Memory Limit: 128 MB Submit: 805  Solved: 380 [id=2754&qu ...

  6. BZOJ 2754: [SCOI2012]喵星球上的点名

    2754: [SCOI2012]喵星球上的点名 Time Limit: 20 Sec  Memory Limit: 128 MBSubmit: 649  Solved: 305[Submit][Sta ...

  7. BZOJ2754: [SCOI2012]喵星球上的点名

    2754: [SCOI2012]喵星球上的点名 Time Limit: 20 Sec  Memory Limit: 128 MBSubmit: 680  Solved: 314[Submit][Sta ...

  8. BZOJ 2754: [SCOI2012]喵星球上的点名 [后缀数组+暴力]

    2754: [SCOI2012]喵星球上的点名 Time Limit: 20 Sec  Memory Limit: 128 MBSubmit: 1906  Solved: 839[Submit][St ...

  9. BZOJ 2754: [SCOI2012]喵星球上的点名 [AC自动机+map+暴力]

    2754: [SCOI2012]喵星球上的点名 Time Limit: 20 Sec  Memory Limit: 128 MBSubmit: 1902  Solved: 837[Submit][St ...

随机推荐

  1. 基于KVM的H3C云计算平台CAS运维经验

  2. slotting filter笔记

    1.slot filling是为了让用户的意图转化为明确的指令而补全信息的过程. 2.准入条件 从一个开放域转入到封闭域,或者从一个封闭域转入到另一个封闭域,中间的跳转是需要逻辑判断的,而这个逻辑判断 ...

  3. SpringCloud学习:Eureka、Ribbon和Feign

    Talk is cheap,show me the code , 书上得来终觉浅,绝知此事要躬行.在自己真正实现的过程中,会遇到很多莫名其妙的问题,而正是在解决这些问题的过程中,你会发现自己之前思维的 ...

  4. Beta阶段基于NABCD评论作品

    组名:杨老师粉丝群 组长:乔静玉 组员:吴奕瑶  刘佳瑞  公冶令鑫  杨磊  刘欣  张宇  卢帝同 一.拉格朗日2018--<飞词> 1.1.NABCD分析 N(Need,需求):该小 ...

  5. 安装Visual studio 2013并进行单元测试

    刚开始在没有老师的指导下自己弄了一个简单的单元测试,最后与老师的对比发现错误百出,于是另起一篇.安装VS2013没有什么问题,安装过程如下图: 接下来别开始练习书上的单元测试. 先是简单的创建C#的类 ...

  6. Leetcode题库——11.盛最多水的容器

    @author: ZZQ @software: PyCharm @file: maxArea.py @time: 2018/10/11 21:47 说明:给定 n 个非负整数 a1,a2,...,an ...

  7. 图论 Kruskal算法 并查集

    #include<iostream> #include<cstring> #include<string> #include<cstdio> #incl ...

  8. angularJS1笔记-(3)-购物车增删改查练习

    html: <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF ...

  9. vue 选项卡(转载)

    !DOCTYPE html> <html> <head> <meta charset="utf-8" /> <meta http-e ...

  10. Beta阶段团队项目开发篇章3

    例会时间 2016.12.6晚 例会照片 个人工作 上阶段任务验收 中英文切换功能已经实现,调查结果分析已经完成,博客基本撰写完成,在征求其他组员意见后发布.任务基本完成. 任务分配 组员 任务内容 ...