[AGC003F] Fraction of Fractal(矩阵乘法)
Description
Snuke从他的母亲那里得到了生日礼物——一个网格。网格有H行W列。每个单元格都是黑色或白色。所有黑色单元格都是四联通的,也就是说,只做水平或垂直移动且只经过黑色单元格即可从任何黑色单元格移动到任何其他黑色单元格。
第i行第j列的单元格的颜色由字符si,j表示。如果si,j是 #,该单元格为黑色;如果si,j是 .,该单元格为白色。至少一个单元格是黑色的。
我们定义「分形」如下:0级分形是一个 1×1的黑色单元格.k级分形由H行W列较小一级的分形按照 Snuke 的网格的样式拼成:与Snuke 网格中的黑色单元格对应的位置是一个k级分形;与Snuke 网格中的白色单元格对应的位置是一个单元格全部为白色,尺寸与k级分形相同的网格。
您将得到 Snuke 的网格的描述和整数 K。请求出K级分形中黑色单元格组成的连通分量数,模1000000007。
Input
第一行三个整数H,W,K如题目描述
接下来H行,每行W个字符
Output
输出K级分形中黑色单元格组成的连通分量数,模1000000007。
题解:
一看 \(K=10^8\) 肯定是log级别的算法,一下想到矩阵快速幂。
首先,一个网格的上面和下面,左边和右边都连通,那么不管怎么分它都是连通的,所以答案是 \(1\)。
如果一个网格上面和下面,左边和右边都不连通,那么不管怎么分都是不连通的,所以答案是 \(x^{k-1}\),\(x\) 为黑块总个数。
剩下就是行连通,列不连通了。(不然转一下就好了)
x[k] 表示 k 级分型有多少个黑块。
y[k] 表示 k 级分型有多少个黑块满足这行的下一个也是黑块。
z[k] 表示 k 级分型有多少行是连通的。
手推可得:
\(x[k]=x[k-1]^2\)
\(y[k]=x[k-1]y[k-1]+z[k-1]y[k-1]\)
\(z[k]=z[k-1]^2\)
构造矩阵:
x & y \\
0 & z
\end{matrix}\right ] \]
求这个矩阵的 \(k-1\) 次方,答案为 \(x-y\)。
CODE:
#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
#define mod 1000000007
int n,m;
char s[1005][1005],tmp[1005][1005];
long long k;
struct Matrix{
long long mat[5][5];
Matrix(){memset(mat,0,sizeof(mat));}
Matrix operator*(const Matrix &b)const{
Matrix c;
for(int i=1;i<=2;i++)
for(int j=1;j<=2;j++){
for(int k=1;k<=2;k++)
c.mat[i][j]+=mat[i][k]*b.mat[k][j];
c.mat[i][j]%=mod;
}
return c;
}
Matrix operator^(long long x)const{
Matrix a(*this),ans;
for(int i=1;i<=2;i++)ans.mat[i][i]=1;
while(x){
if(x&1)ans=ans*a;
x>>=1,a=a*a;
}
return ans;
}
}mat;
int qpow(int x,long long y){
int ans=1;
while(y){
if(y&1)ans=1LL*ans*x%mod;
y>>=1,x=1LL*x*x%mod;
}
return ans;
}
bool check(){
for(int i=1;i<=n;i++)
if(s[i][1]=='#'&&s[i][m]=='#')return true;
return false;
}
void turn(){
for(int i=1;i<=n;i++)
for(int j=1;j<=m;j++)
tmp[m-j+1][i]=s[i][j];
swap(n,m);
memcpy(s,tmp,sizeof(s));
}
int main(){
scanf("%d%d%lld",&n,&m,&k);
int x=0,y=0,z=0;
for(int i=1;i<=n;i++){
scanf("%s",s[i]+1);
for(int j=1;j<=m;j++)x+=s[i][j]=='#';
}
bool a=check(),b=(turn(),check());turn();
if(a&&b)return printf("1"),0;
else if(!a&&!b)return printf("%d",qpow(x,k-1)),0;
else if(b)turn();
for(int i=1;i<=n;i++)
z+=s[i][1]=='#'&&s[i][m]=='#';
for(int i=1;i<=n;i++)
for(int j=1;j<m;j++)y+=s[i][j]=='#'&&s[i][j+1]=='#';
mat.mat[1][1]=x,mat.mat[1][2]=y,mat.mat[2][2]=z;
mat=mat^(k-1);
printf("%lld",(mat.mat[1][1]-mat.mat[1][2]+mod)%mod);
}
[AGC003F] Fraction of Fractal(矩阵乘法)的更多相关文章
- [AGC003F] Fraction of Fractal 矩阵快速幂
Description SnukeSnuke从他的母亲那里得到了生日礼物--一个网格.网格有HH行WW列.每个单元格都是黑色或白色.所有黑色单元格都是四联通的,也就是说,只做水平或垂直移动且只经过 ...
- @atcoder - AGC003F@ Fraction of Fractal
目录 @description@ @solution@ @accepted code@ @details@ @description@ 给定一个 H*W 黑白格图,保证黑格四连通. 定义分形如下:0 ...
- [agc003F]Fraction of Fractal
Description 传送门 Solution 本篇博客思路来自大佬的博客(侵删). 我们定义如果网格的第一行和最后一行的第i列都为黑色,则它是一个上下界接口.左右界接口定义同上. 如果上下界接口和 ...
- *HDU2254 矩阵乘法
奥运 Time Limit: 1000/1000 MS (Java/Others) Memory Limit: 65536/65536 K (Java/Others)Total Submissi ...
- *HDU 1757 矩阵乘法
A Simple Math Problem Time Limit: 3000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Ot ...
- CH Round #30 摆花[矩阵乘法]
摆花 CH Round #30 - 清明欢乐赛 背景及描述 艺术馆门前将摆出许多花,一共有n个位置排成一排,每个位置可以摆花也可以不摆花.有些花如果摆在相邻的位置(隔着一个空的位置不算相邻),就不好看 ...
- POJ3070 Fibonacci[矩阵乘法]
Fibonacci Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 13677 Accepted: 9697 Descri ...
- bzoj 2738 矩阵乘法
其实这题跟矩阵乘法没有任何卵关系,直接整体二分,用二维树状数组维护(刚刚学会>_<),复杂度好像有点爆炸(好像有十几亿不知道是不是算错了),但我们不能怂啊23333. #include&l ...
- 【BZOJ-2476】战场的数目 矩阵乘法 + 递推
2476: 战场的数目 Time Limit: 1 Sec Memory Limit: 128 MBSubmit: 58 Solved: 38[Submit][Status][Discuss] D ...
随机推荐
- LGTB 学分块
总时间限制: 10000ms 单个测试点时间限制: 1000ms 内存限制: 65536kB 描述 LGTB 最近在学分块,但是他太菜了,分的块数量太多他就混乱了,所以只能分成 3 块 今天他得 ...
- 二、Shell 变量
Shell 变量 定义变量时,变量名不加美元符号($,PHP语言中变量需要),如: your_name="runoob.com" 注意,变量名和等号之间不能有空格,这可能和你熟悉的 ...
- web项目中无法开启或404
404找不到页面,可能是spring的bean自动注入有了问题,例如org.springframework.beans.factory.BeanCreationException:可以检查配置文件的s ...
- __setitem__,__getitem,__delitem__的作用
class Foo: def __init__(self, name): self.name = name def __getitem__(self, item): print('obj[key]时, ...
- [Hdu3555] Bomb(数位DP)
Description 题意就是找0到N有多少个数中含有49. \(1\leq N \leq2^{63}-1\) Solution 数位DP,与hdu3652类似 \(F[i][state]\)表示位 ...
- Java程序占用实际内存大小
很多人错误的认为运行Java程序时使用-Xmx和-Xms参数指定的就是程序将会占用的内存,但是这实际上只是Java堆对象将会占用的内存.堆只是影响Java程序占用内存数量的一个因素.要更好的理解你的J ...
- U10783 名字被和谐了
U10783 名字被和谐了 题目背景 众所周知,我们称g是a的约数,当且仅当g是正数且a mod g = 0. 众所周知,若g既是a的约数也是b的约数,我们称g是a.b的一个公约数. 众所周知,a.b ...
- mysql sum聚合函数和if()函授的联合使用
今天去面试遇到一个数据库试题,首先说一下表结构如下: 表结构:mytest 表数据:mytest 要查询的结果如下: 在本题目中,需要用到sum聚合函数和if函数 sql如下: ,)) ,)) AS ...
- va_list
void Log( const TCHAR *pszFormat, ... ) { TCHAR buf[] ; va_list arglist ; try { _tcscpy_s ( buf, , _ ...
- PHP 获取客户端用户 IP 地址
一般情况下可以使用以下代码获取到用户 IP 地址 echo 'User IP - '.$_SERVER['REMOTE_ADDR']; // 服务器在局域网的话,那么显示的则是内网IP .// 如果服 ...