分析:

考试的时候由于一些神奇的原因(我就不说是什么了)...没有想$C$题,直接交了个暴力上去...

然后发现暴力的数组开的太大,由于矩阵乘法的需要做$m$次初始化,所以只拿到了10分...

我们一步一步来挖掘题目中隐含的条件...

首先,这个矩阵乘法很特殊,是位运算的形式,那么也就是说,每一位的运算是独立的,所以我们可以拆位,处理每一位的运算...

然后考虑对于其中的一位如何快速计算一个矩阵的$n$次幂...考虑到每一个格子只有可能是$0$或$1$,观察发现,对于数字$a[i][j]$,只有当第$i$行和第$j$列是相同的时候,我们新的到的矩阵中$a[i][j]$才是$0$,否则因为是$or$运算,所以只要有一位不同就是$1$...

那么我们考虑$A^{m-1}*A=A^{m}$,记$X=A^{m-1}$,$Y=A^m$,我们考虑$X$的每一个行向量对应的$Y$中的行向量是什么样子的,如果当前的行向量和$A$中的任意一个列向量都相等的话,那么新得到的行向量就是一个全为$1$的向量,否则,最多只有可能有$n$种取值,现在我们假设$A$中的每一个列向量都互不相同,那么也就是说,当前的行向量只有可能有一个地方是$0$,这个$0$最多有$n$中位置...所以当前行向量所对应的结果中的行向量最多有$n+1$种取值...因为每一次我们乘上的矩阵都是相同的,所以说无论进行多少次乘法,我们都只有可能在$n+1$种取值中给行向量赋值...那么也就是说,现在我们有一个$n+1$个点的图,然后我们需要在这张图上走$m-1$步,那么就可以倍增找到答案...至于对于图的预处理我们可以用$bitset$来加速...

没有想出来的原因:

没有充分利用到位运算的性质区进行拆位,没有想到去考虑每个行向量所对应的结果是存在循环的...

代码:

一开始实在不理解怎么做所以直接抄了一遍$std$...

#include<algorithm>
#include<iostream>
#include<cstring>
#include<cstdio>
//by NeighThorn
using namespace std; const int maxn=500+5; int n,m,tot,a[maxn][maxn],f[maxn<<1][30],id[maxn],ans[maxn][maxn]; struct M{ unsigned long long a[8]; friend bool operator == (M x,M y){
for(int i=0;i<=7;i++)
if(x.a[i]!=y.a[i])
return false;
return true;
} inline void modify(int pos,int x){
a[pos>>6]|=1ULL<<(pos&63);
if(!x)
a[pos>>6]^=1ULL<<(pos&63);
} inline bool query(int pos){
return (a[pos>>6]>>(pos&63))&1;
} }colu[maxn],node[maxn<<1]; inline int build(void){
for(int i=1;i<=tot;i++)
if(node[i]==node[tot+1])
return i;
int res=++tot;
for(int i=1;i<=n;i++)
node[tot+1].modify(i,!(node[res]==colu[i]));
f[res][0]=build();
return res;
} signed main(void){
freopen("C.in","r",stdin);
freopen("C.out","w",stdout);
scanf("%d%d",&n,&m);m--;
for(int i=1;i<=n;i++)
for(int j=1;j<=n;j++)
scanf("%d",&a[i][j]);
for(int i=0;i<=30;i++){
for(int j=1;j<=n;j++)
for(int k=1;k<=n;k++)
colu[j].modify(k,(a[k][j]>>i)&1);
tot=0;
for(int j=1;j<=n;j++){
for(int k=1;k<=n;k++)
node[tot+1].modify(k,(a[j][k]>>i)&1);
id[j]=build();
}
for(int j=1;j<=29;j++)
for(int k=1;k<=tot;k++)
f[k][j]=f[f[k][j-1]][j-1];
for(int j=0;j<=29;j++)
if(m&(1<<j))
for(int k=1;k<=n;k++)
id[k]=f[id[k]][j];
for(int j=1;j<=n;j++)
for(int k=1;k<=n;k++)
ans[j][k]|=node[id[j]].query(k)<<i;
}
for(int i=1;i<=n;i++,puts(""))
for(int j=1;j<=n;j++)
printf("%d ",ans[i][j]);
return 0;
}
/*
Never give up.
Bless all.
*/

  


By NeighThorn

GDOI2015的某道题目的更多相关文章

  1. C语言超级经典400道题目

    C语言超级经典400道题目 1.C语言程序的基本单位是____ A) 程序行 B) 语句 C) 函数 D) 字符.C.1 2.C语言程序的三种基本结构是____构A.顺序结构,选择结构,循环结 B.递 ...

  2. hdu 动态规划(46道题目)倾情奉献~ 【只提供思路与状态转移方程】(转)

    HDU 动态规划(46道题目)倾情奉献~ [只提供思路与状态转移方程] Robberies http://acm.hdu.edu.cn/showproblem.php?pid=2955      背包 ...

  3. 小白欢乐多——记ssctf的几道题目

    小白欢乐多--记ssctf的几道题目 二哥说过来自乌云,回归乌云.Web400来源于此,应当回归于此,有不足的地方欢迎指出. 0x00 Web200 先不急着提web400,让我们先来看看web200 ...

  4. 在 n 道题目中挑选一些使得所有人对题目的掌握情况不超过一半。

    Snark and Philip are preparing the problemset for the upcoming pre-qualification round for semi-quar ...

  5. SQL的几道题目

    1.构造数据插入方案表t_project_finish表 a)将addtime更新为当前时间的前一天 首先想到的是addtime=addtime-1,然后就开始验证这个想法. 插入一行数据,包括主键和 ...

  6. codeforces 几道题目

    BZOJ挂了....明天就要出发去GDKOI了....不能弃疗. 于是在cf水了几道题, 写写详(jian)细(dan)题解, 攒攒RP, 希望GDKOI能好好发挥.......  620E. New ...

  7. leetcode 几道题目

    是周六晚上的几道题,晚上11点半,睡的早,起不来! 494. Target Sum 分析:看完这题,看到数据范围,长度20,枚举就是1<<20 = 1e6, 然后单次20,总共就是2e8, ...

  8. C++面试出现频率最高的30道题目

    http://blog.csdn.net/wangshihui512/article/details/9092439 1.new.delete.malloc.free关系 delete会调用对象的析构 ...

  9. 从几道题目带你深入理解Event Loop_宏队列_微队列

    目录 深入探究JavaScript的Event Loop Event Loop的结构 回调队列(callbacks queue)的分类 Event Loop的执行顺序 通过题目来深入 深入探究Java ...

随机推荐

  1. 面试官常问的10个Linux问题

    1.如何暂停一个正在运行的进程,把其放在后台(不运行)? 为了停止正在运行的进程,让其再后台运行,我们可以使用组合键Ctrl+Z. 2.什么是安装Linux所需的最小分区数量,以及如何查看系统启动信息 ...

  2. stm8编程tips(stvd)

    编译完成时显示程序占用的flash和ram大小 将附件压缩包中的mapinfo.exe解压到stvd的安装路径\stvd中 在工程上点右键选settings 右侧的选项卡选择Linker,将categ ...

  3. 「暑期训练」「Brute Force」 Restoring Painting (CFR353D2B)

    题意 给定一定条件,问符合的矩阵有几种. 分析 见了鬼了,这破题谁加的brute force的标签,素质极差.因为范围是1e5,那你平方(枚举算法)的复杂度必然爆. 然后你就会思考其中奥妙无穷的数学规 ...

  4. 「日常训练」Phone Numbers (CFR466D2C)

    题意(Codeforces 940C) 给定一字符串,求比它字典序大的字符串.限定其长度,并且只能用原串的字母. 分析 考虑原串长度lorigin与给定的长度lgiven.若给定长度大于原串长度,直接 ...

  5. 最小总代价 状压DP

    描述 n个人在做传递物品的游戏,编号为1-n. 游戏规则是这样的:开始时物品可以在任意一人手上,他可把物品传递给其他人中的任意一位:下一个人可以传递给未接过物品的任意一人. 即物品只能经过同一个人一次 ...

  6. fiddler之弱网测试

    今天就说一下如何使用fiddler做弱网测试 1.首先要把手机的代理打开,这就不多讲了哈,不懂得话请点传送门:https://www.cnblogs.com/fuxinxin/p/9146693.ht ...

  7. 第十九章 Python os模块,pathlib 判断文件是目录还是文件

    OS模块 os.path.abspath() :返回path规范化的绝对路径 import sys import os BASE_DIR = os.path.dirname(os.path.dirna ...

  8. Java并发基础--线程安全

    一.线程安全 1.线程安全的概念 线程安全:某个类被单个线程,或者多个线程同时访问,所表现出来的行为是一致,则可以说这个类是线程安全的. 2.什么情况下会出现线程安全问题 在单线程中不会出现线程安全问 ...

  9. 排查实时tail功能cpu占用过高问题

    “你的python应用cpu占用快90%了!!!”,良哥朝我眨了眨布满血丝的眼睛“不会吧”,我心想:我这是好的啊 没接触过kafka的同学可以先了解下:([http://www.jasongj.com ...

  10. 分享 go语言爬虫---开源项目Pholcus

    写在开头的话:记录一下最近学习Pholcus(https://github.com/henrylee2cn/pholcus)的过程,首先去学习的go基本语法,在没接触的时候发现很多不理解的地方,但是当 ...