首页 > 其他分享 >P9108 [PA2020] Malowanie płotu

P9108 [PA2020] Malowanie płotu

时间:2025-01-08 20:23:16浏览次数:1  
标签:le int sum s0 add PA2020 otu Malowanie mod

P9108 [PA2020] Malowanie płotu

题意

有一个 \(n \times m\) 的方格,你需要对每一列涂一个非空连续段,要求相邻列的涂色连续段有交。问涂色方案数。

\(n \times m \le 10^7\)。

思路

我们需要一个 \(O(nm)\) 的算法,但是不好直接设一个 \(O(nm)\) 的状态。

很容易想到设 \(f_{i,l,r}\) 表示考虑到第 \(i\) 列,第 \(i\) 列涂 \([l,r]\) 的方案数。

\[f_{i,l,r} = \sum_{[l',r'] \cap [l,r] \neq \emptyset} f_{i-1,l',r'} \]

然后你发现这个交非空直接做是一个三维偏序,可以差分成二维偏序,但是仍然很麻烦。

考虑经典的,变成求全集减去不交的,即:

\[f_{i,l,r} = \sum_{l' \le r'} f_{i-1,l',r'} - \sum_{l' \le r' < l} f_{i-1,l',r'} - \sum_{r < l' \le r'} f_{i-1,l',r'} \]

然后我们就可以设

\[s0_{i,j} = \sum_{l \le r \le j} f_{i,l,r},s1_{i,j} = \sum_{j \le l \le r} f_{i,l,r}\\ f_{i,l,r} = s0_{i-1,m} - s0_{i-1,l-1} - s1_{i-1,r+1} \]

这样就可以状态 \(O(nm^2)\),转移 \(O(1)\) 做到总共 \(O(nm^2)\) 的复杂度了。


我们可爱的 \(s\) 数组状态只有 \(O(nm)\)。考虑直接转移 \(s\)。

\[\begin{aligned} s0_{i,j} & = s0_{i,j-1} + \sum_{l\le j} f_{i,l,j}\\ & = s0_{i,j-1} + \sum_{l \le j} s0_{i-1,m} - s0_{i-1,l-1} - s1_{i-1,j+1}\\ & = s0_{i,j-1} + j(s0_{i-1,m} - s1_{i-1,j+1}) - \sum_{l \le j} s0_{i-1,l-1} \end{aligned} \]

\[t0_{i,j} = \sum_{k \le j} s0_{i,k} \]

\[s0_{i,j} = s0_{i,j-1} + j(s0_{i-1,m} - s1_{i-1,j+1}) - t0_{i-1,j-1} \]

同理,有:

\[t1_{i,j} = \sum_{k \ge j} s1_{i,j}\\ s1_{i,j} = s1_{i,j+1} + (m-j+1)(s0_{i-1,m} - s0_{i-1,j-1}) - t1_{i-1,r+1} \]

初始 \(f_{1,l,r} = 1\),即 \(s0_{1,i} = \frac{i(i-1)}{2} + i,s1_{1,i} = \frac{(m-i+1)(m-i)}{2} + m-i+1\),答案是 \(\sum f_{n,l,r}\),即 \(f0_{n,m}\)。

时间复杂度 \(O(nm)\)。

code

要注意一点边界细节。

#include<bits/stdc++.h>
#define sf scanf
#define pf printf
#define rep(x,y,z) for(int x=y;x<=z;x++)
#define per(x,y,z) for(int x=y;x>=z;x--)
using namespace std;
typedef long long ll;
namespace hesitate {
	constexpr int N=1e7+7;
	int mod;
	int add(int a,int b) { return a+b>=mod ? a+b-mod : a+b; }
	void _add(int &a,int b) { a=add(a,b); }
	int mul(int a,int b) { return 1ll*a*b%mod; }
	void _mul(int &a,int b) { a=mul(a,b); }
	int n,m;
	int s[2][N],t[2][N];
	void main() {
		sf("%d%d%d",&n,&m,&mod);
		rep(j,0,m-1) s[0][j]=add(1ll*j*(j+1)/2%mod,j+1), s[1][j]=add(1ll*(m-j)*(m-j-1)/2%mod,m-j); 
		t[0][0]=s[0][0], t[1][m-1]=s[1][m-1];
		rep(j,1,m-1) t[0][j]=add(t[0][j-1],s[0][j]);
		per(j,m-2,0) t[1][j]=add(t[1][j+1],s[1][j]);
		rep(i,1,n-1) {
			s[0][i*m]=add(s[0][i*m-1],mod-s[1][(i-1)*m+1]);
			t[0][i*m]=s[0][i*m];
			rep(j,1,m-1) {
				int k=i*m+j;
				s[0][k]=add(s[0][k-1],add(mul(j+1,add(s[0][i*m-1],mod-s[1][(i-1)*m+j+1])),mod-t[0][(i-1)*m+j-1]));
				t[0][k]=add(t[0][k-1],s[0][k]);
			}
			s[1][i*m+m-1]=add(s[0][i*m-1],m==1 ? 0 : mod-s[0][i*m-2]);
			t[1][i*m+m-1]=s[1][i*m+m-1];
			per(j,m-2,0) {
				int k=i*m+j;
				s[1][k]=add(s[1][k+1],add(mul(m-j,add(s[0][i*m-1],j==0 ? 0 : mod-s[0][(i-1)*m+j-1])),mod-t[1][(i-1)*m+j+1]));
				t[1][k]=add(t[1][k+1],s[1][k]);
			}
		}
		pf("%d\n",s[0][n*m-1]);
	}
}
int main() {
    #ifdef LOCAL
    freopen("in.txt","r",stdin);
    freopen("my.out","w",stdout);
    #endif
	hesitate :: main();
}

标签:le,int,sum,s0,add,PA2020,otu,Malowanie,mod
From: https://www.cnblogs.com/liyixin0514/p/18660383

相关文章

  • 『AotuHotKey』——一个小巧却高效的实用效率工具
    [!note]本来主要是想找一下「」和『』,然后这个方法直接可以找到大部分的特殊字符通过输入法输出『Ctr+shift+Z』进入搜狗输入法的『符号大全』在『标点符号』项可以找到「」和『』使用AutoHotKey自定义替换[!note]每次想要用到这两个符号的时候都要进入输入......
  • [USACO2018Jan白银] 牛tube (MooTube)
    题目描述在业余时间,FarmerJohn创建了一个新的视频共享服务,他将其命名为MooTube。在MooTube上,FarmerJohn的奶牛可以录制,分享和发现许多有趣的视频。他的奶牛已经发布了 N个视频(1≤N≤5000),为了方便将其编号为1…N 。然而,FJ无法弄清楚如何帮助他的奶牛找到他们可能喜......
  • 【小白51单片机专用教程】protues仿真AT89C51入门
    课程特点无需开发板0基础教学软件硬件双修辅助入门        本课程面对纯小白,因此会对各个新出现的知识点在实例基础上进行详细讲解,有相关知识的可以直接跳过。课程涉及protues基本操作、原理图设计、数电模电、kell使用、C语言基本内容,所有涉及知识都将建立在实例的......
  • (六)Protues仿真STM32单片机控制8x8LED显示
    (六)Protues仿真STM32单片机控制8x8LED显示–ARMFUN1,配置CUBEMX,将PA0~7,PAB0~7配置为GPIOOUTPUT模式2,GPIOA负责8bit数据,高电平有效,GPIOB负责行选则,低电平有效,编写行刷新函数voiddisp_set_row(unsignedchardat,charsel){ GPIOB->ODR=0xff;//关闭行选,防止将数据......
  • 痞子衡嵌入式:MCUBootUtility v6.3发布,支持获取与解析启动日志
    --痞子衡维护的NXP-MCUBootUtility工具距离上一个大版本(v5.3.0)发布过去一年了,期间痞子衡也做过三个版本更新,但不足以单独介绍。这一次痞子衡为大家带来了全新重要版本v6.3.x,这次更新主要是想和大家特别聊聊ROM启动日志这个特性的支持。一、v6.0-v6.3更新记录--v5.......
  • P4185 [USACO18JAN] MooTube G 题解
    水一篇题解。也是一道并查集的好题,涉及另一个并查集的基本应用,并查集维护连通块(我跟并查集过不去了???)大致题意:给你一棵树,对于每次询问求一个点所在连通块中到达该点的最小路径权值大于给定值的点个数。既然都连通块了,那我们在维护连通块的时候直接不把权值大于K的边加进去,用并查......
  • LG P9108 [PA2020] Malowanie płotu
    状态数是\(O(nm^2)\)的DP很好想,就是\(dp_{i,l,r}\)表示第\(i\)次的区间为\([l,r]\)的方案数。但是这个状态数就已经死了,而题目又提示\(n\timesm\leq1e7\),说明状态只能形如\(dp_{i,j}\)。这时就会想到一个简陋的打补丁方式:设\(f_{i,l},g_{i,r}\)分别表示第\(i\)......
  • P9108 [PA2020] Malowanie płotu
    题意:给定\(n,m\),一个区间序列\(\{[L_1,R_1],[L_2,R_2],\cdots,[L_n,R_n]\}\)被称为好的当且仅当:\(\foralli\in[1,n],1\leL_i\leR_i\lem\)。\(\foralli\in[1,n-1],[L_i,R_i]\cup[L_{i+1},R_{i+1}]\ne\emptyset\)。输出好的序列个数对给定质数\(p\)......
  • 利用蓝莲花BlueLotus通过XSS获取Cookie
    蓝莲花BlueLotus_XSSReceiver清华大学蓝莲花战队做的一个平台,优点是足够小,不需要数据库,只要有个能运行php的环境就可以了,缺点是一般只适合一个人用。配置蓝莲花拉取dockerdockerpullromeoz/docker-apache-php:5.6上传文件文件下载地址:https://github.com/trysec/......
  • 0008、基于51单片机protues仿真的双机通信设计(仿真图、源代码、讲解视频)
    0008、基于51单片机protues仿真的双机通信设计(仿真图、源代码、讲解视频)该设计为51单片机protues仿真的双机通信设计,实现双机通信、数据交互等功能;功能实现如下:使用51单片机实现双机通信,T1作为波特率发生器,使用工作模式1,中断实现,在PROTEUS上仿真实现.要求如下:1、单片机1发......