#dp,排列#LOJ 2743「JOI Open 2016」摩天大楼
题目
将互不相同的 \(n\) 个数重排,使得相邻两数差的总和不超过 \(L\) 的有多少种方式。
\(n\leq 100,L\leq 1000\)
分析
对于排列的问题,有一种很妙的方法就是从小到大插入,
若升序数列 \(B\),\(B_{i+1}-B_i\) 对答案产生贡献
当且仅当相邻两数 \(x\leq B_i,y\geq B_{i+1}\)
那么在 \(B_1\) 到 \(B_i\) 排列后可以添加的位置就能产生贡献,
也就是与段数有关,而且要考虑左右边界。
设 \(dp[i][j][k][opt]\) 表示升序后前 \(i\) 个数,依次被分成 \(j\) 段,
目前确定 \(opt\) 个边界(边界不能新开一段),总和为 \(k\) 的方案数。
由 \(i-1\) 过渡到 \(i\) 的贡献即是 \(t=(j*2-opt)*(B_{i}-B_{i-1})\)
新开一段(不充当边界): \(dp[i][j+1][k][opt]+=dp[i-1][j][k-t][opt]*(j+1-opt)\)
合并一段:\(dp[i][j-1][k][opt]+=dp[i-1][j][k-t][opt]*(j-1)\)
将这个数放在段首或段尾(不包含边界): \(dp[i][j][k][opt]+=dp[i-1][j][k-t][opt]*(j*2-opt)\)
将这个数新开一段并作为边界: \(dp[i][j+1][k][opt+1]+=dp[i-1][j][k-t][opt]*(2-opt)\)
将这个数作为边界但不新开一段: \(dp[i][j][k][opt+1]+=dp[i-1][j][k-t][opt]*(2-opt)\)
最后答案为 \(\sum_{i=0}^L dp[n][1][i][2]\),注意当 \(n=1\) 时要特判。
代码
#include <cstdio>
#include <cctype>
#include <algorithm>
using namespace std;
const int N=111,mod=1000000007;
int dp[N][N][N*10][3],n,m,a[N],ans;
int iut(){
int ans=0; char c=getchar();
while (!isdigit(c)) c=getchar();
while (isdigit(c)) ans=ans*10+c-48,c=getchar();
return ans;
}
void Mo(int &x,int y){x=x+y>=mod?x+y-mod:x+y;}
int main(){
n=iut(),m=iut();
if (n==1) return !printf("1");
for (int i=1;i<=n;++i) a[i]=iut();
sort(a+1,a+1+n),a[0]=a[1];
dp[0][0][0][0]=1;
for (int i=1;i<=n;++i)
for (int j=0;j<i;++j)
for (int opt=0;opt<3;++opt){
if (j*2<opt) break;
int t=(j*2-opt)*(a[i]-a[i-1]);
for (int k=t;k<=m;++k)
if (dp[i-1][j][k-t][opt]){
int now=dp[i-1][j][k-t][opt];
Mo(dp[i][j+1][k][opt],(j+1ll-opt)*now%mod);
Mo(dp[i][j][k][opt],(j*2ll-opt)*now%mod);
if (j) Mo(dp[i][j-1][k][opt],(j-1ll)*now%mod);
if (opt==2) continue;
Mo(dp[i][j+1][k][opt+1],(2ll-opt)*now%mod);
Mo(dp[i][j][k][opt+1],(2ll-opt)*now%mod);
}
}
for (int i=0;i<=m;++i) Mo(ans,dp[n][1][i][2]);
return !printf("%d",ans);
}
#dp,排列#LOJ 2743「JOI Open 2016」摩天大楼的更多相关文章
- [LOJ#2743][DP]「JOI Open 2016」摩天大楼
题目传送门 DP 经典题 考虑从小到大把数加入排列内 如下图(\(A\) 已经经过排序): 我们考虑如上,在 \(i\) ( \(A_i\) )不断增大的过程中,维护上面直线 \(y=A_i\) 之下 ...
- [题解] [LOJ2743]「JOI Open 2016」摩天大楼
题目大意 将 \(N\) 个互不相同的整数 \(A_1 , A_2 , ⋯ , A_N\) 任意排列成 \(B_1 , B_2 , ⋯ , B_N\) . 要求 \(∑^{N−1}_{i=1} |B_ ...
- LOJ#2351. 「JOI 2018 Final」毒蛇越狱
LOJ#2351. 「JOI 2018 Final」毒蛇越狱 https://loj.ac/problem/2351 分析: 首先有\(2^{|?|}\)的暴力非常好做. 观察到\(min(|1|,| ...
- LOJ#2764. 「JOI 2013 Final」JOIOI 塔
题目地址 https://loj.ac/problem/2764 题解 真的想不到二分...不看tag的话... 考虑二分答案转化为判定问题,那么问题就变成了能不能组合出x个JOI/IOI,考虑贪心判 ...
- loj 3014「JOI 2019 Final」独特的城市
loj 我本来是直接口胡了一个意思一样的做法的,但是因为觉得有点假+实现要用并查集(?)就卡了好一会儿... 对于一个点\(x\)来说,独特的点一定在它的最长链上,如果有独特的点不在最长链上,那么最长 ...
- loj 2759「JOI 2014 Final」飞天鼠
loj 这题有在一棵树上上升或者下降的操作,稍加分析后可以发现上升操作如果不是一定要做(指高度不足以到下一棵树或者是最后到达\(n\))就不做,下降操作也是如果不是一定要做(指到达下一棵树时高度过高) ...
- loj 2336「JOI 2017 Final」绳
loj 首先,所有位置最多被染色一次,因为要染多次的话,还不如一开始就染成最终的颜色.并且你可以一开始就染好色 因为最终长度为2,那么如果染完后这个序列可以被折完,那么首先最多只有两种颜色,还有就是要 ...
- loj#2334 「JOI 2017 Final」JOIOI 王国
分析 二分答案 判断左上角是否满足 为了覆盖所有范围 我们依次把右下角,左上角,右上角移动到左上角 代码 #include<bits/stdc++.h> using namespace s ...
- loj#2333 「JOI 2017 Final」准高速电车
分析 我们发现到达一个点一定是先快车再准快车再慢车 于是快车将1-n分为多个区间 每次取出每个区间当前能到达的点的数量 选剩余时间贡献最大的的一个取得贡献并且再能到达的最远点建立准快车 代码 #inc ...
- loj#2332 「JOI 2017 Final」焚风现象
分析 我们发现改变一个区间实际上只有两个端点的贡献变换 代码 #include<bits/stdc++.h> using namespace std; #define int long l ...
随机推荐
- 解决Spring boot 单元测试,无法读取配置文件问题。
1.启动类上加上@EnableConfigurationProperties 2.springboot版本springboot 2.X版本在单元测试中读取不到yml配置文件的值这是个大坑,在项目中写单 ...
- 使用俩个链接在一起的容器运行wordpress
# 问题,如何分离mysql和wordpress,使它们每个都单独运行一个容器. # 解决办法:运行时通过--link选项使它们链接在一起 --link <container_name>: ...
- 问题:RuntimeError: Model class LuffyAPI.apps.user.models.UserInfo doesn't declare an explicit app_label and isn't in an application in INSTALLED_APPS.
问题截图 报错原因 提示app未注册,但实际上已经注册的 1. # settings配置文件移动后要将这个settings添加到环境变量中 sys.path.insert(0, BASE_DIR) # ...
- 腾讯云视频转码回调 http code 405
异常信息 405 Method Not Allowed 异常场景 通过腾讯云SDK上传视频,视频转码完成回调我的接口失败,我这边一直没有log.找到腾讯云工作人员,告诉我这边返回405错误和不支持ge ...
- logback中使用MDC自定义日志输出格式
logback-MDC 相当于自定义日志格式输出 写在过滤器中 示例: try { Context context = createContext(request, response); proces ...
- 【Azure APIM】解决APIM Self-hosted Gateway在AKS上,最开始访问时候遇见的404问题
问题描述 根据APIM官方文档,创建Self-hosted 网关在AKS中( 使用 YAML 将自承载网关部署到 Kubernetes :https://docs.azure.cn/zh-cn/api ...
- 使用debezium实现cdc实时数据同步功能记录
Debezium 是一个用于变更数据捕获的开源分布式平台.能够保证应用程序就可以开始响应其他应用程序提交到您数据库的所有插入.更新和删除操作.Debezium 持久.快速,因此即使出现问题,您的应用程 ...
- Cookie session token 区别?
Cookie一开始为了解决登录状态的问题,token是为了对保存的数据进行加密,加密了之后cookie就保存了加密之后的密文,这个就是token,session是因为数据保存到客户端不安全,把数据保存 ...
- Java 线程通信的应用:经典例题:生产者/消费者问题
1 package bytezero.threadcommunication; 2 3 /** 4 * 线程通信的应用:经典例题:生产者/消费者问题 5 * 6 * 7 * 8 * @author B ...
- 菜单导航tab切换样式的小技巧
1.最终效果 2.HTML结构 <div class="licaiMenu"> <ul class="navi"> <li> ...