Codeforces 400C 矩阵乘法 数学规律
2024-10-08 18:28:13
今天下午Virtual了一套最近的CF题,第三题给TLE了,就跑过去上课了。
这题给定一个由二进制表示的矩阵,当询问3的时候,求矩阵的值,矩阵的值是所有第i行乘以第i列的值的总和,然后还有1 b是翻转b行的数字 2 b是翻转b列的数字
一开始没怎么考虑复杂度,就直接想暴力过,觉得只要把翻转先暂存,最后有询问3的时候再pushdown再计算一下结果。。。简直不经大脑思考,有10^6询问,我这样做,如果询问全部是3,那光是计算矩阵10^6次就能达到12次方的复杂度。。。真是一点都不考虑。。。
后来在课上想了点方法,觉得把每一行和列的翻转都预处理一下,以及先把原始结果预处理出来,然后遇到翻转就跟之前的状态比一下看看要不要翻转结果的值。、。。遇到3就可以直接输出了,这样做还是WA了。。。
结果后来搜题解,发现,这个题目真的是个规律水题啊啊啊。。。很明显,n*n的矩阵如果是按i行与i列相乘的和作为结果的话,那么非对角线的元素都会与对称位相乘,并且还会加两次,同一个二进制值相加两次,那不就相当于没加,也就是说只有对角线的元素对结果有影响。。。。
想到这里真是要哭了,那不就很简单的一题目,先按位跟对角线的值异或得到初始结果,然后底下但凡有翻转操作,就把结果翻转(因为每次行或者列的翻转必定造成对角线某个元素翻转,也就直接造成结果翻转)。。然后遇到3直接输出结果即可啦
#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
int mat[][];
//int row[1010],col[1010]
int n,q;
//int change[1010][2][2];
//int pr[1010],pc[1010];
//void putdown()
//{
// for (int i=1;i<=n;i++)
// {
// if (row[i])
// {
// for (int j=1;j<=n;j++)
// {
// mat[i][j]^=1;
// }
// row[i]=0;
// }
// if (col[i])
// {
// for (int j=1;j<=n;j++)
// {
// mat[j][i]^=1;
// }
// col[i]=0;
// }
// }
//}
//int counts()
//{
// int ans=0;
// for (int i=1;i<=n;i++)
// {
// int t=0;
// for (int j=1;j<=n;j++)
// {
// int tmp=mat[i][j]*mat[j][i];
// ans+=tmp;
// t+=tmp;
// //change[i][0][0]=tmp;
// }
// change[i][0][0]=t%2;
// }
// ans%=2;
// return ans;
//
//}
//void init()
//{
// for (int i=1;i<=n;i++)
// {
// int t1,t2,t3;
// t1=t2=t3=0;
// for (int j=1;j<=n;j++)
// {
//
// if (j==1)
// {
// t1+=(1-mat[i][j])*(1-mat[j][i]);
// t2+=(1-mat[i][j])*(1-mat[j][i]);
// t3+=(1-mat[i][j])*(1-mat[j][i]);
// }
// else
// {
// t1+=(1-mat[i][j])*mat[j][i];
// t2+=mat[i][j]*(1-mat[j][i]);
// t3+=(1-mat[i][j])*(1-mat[j][i]);
// }
// }
// change[i][1][0]=t1%2;
// //change[i][1][0]^=change[i][0][0];
//
// change[i][0][1]=t2%2;
// //change[i][0][1]^=change[i][0][0];
//
// change[i][1][1]=t3%2;
// //change[i][1][1]^=change[i][0][0];
// //cout<<change[i][1][0]<<" "
// }
//}
int main()
{
int a,b;
// freopen("CF_238.txt","w",stdout);
while (scanf("%d",&n)!=EOF)
{
for (int i=;i<=n;i++)
{
for (int j=;j<=n;j++)
{
scanf("%d",&mat[i][j]);
}
//pr[i]=pc[i]=0;
}
int ans=;
for (int i=;i<=n;i++)
ans=ans^mat[i][i];
//init();
//int ans=counts(); scanf("%d",&q);
for (int i=;i<q;i++)
{
scanf("%d",&a);
if (a<)
{
scanf("%d",&b);
ans^=;
}
else
{
//putdown();
//counts();
printf("%d",ans);
}
}
printf("\n");
}
}
最新文章
- java利用JDK调用并执行js源码
- 00.PHP学习建议
- 【转】【异常处理】Incorrect string value: &#39;\xF0\x90\x8D\x83...&#39; for column... Emoji表情字符过滤的Java实现
- MVC4/5+jquery+bootstrap样式+dataTables+linq+WCF+EF6后台和前台的框架集合!好蛋疼哦!数据库支持MYSQL 和MSSQL,oracle。集成腾讯企业邮箱收邮件同步用户SSO登陆等功能。
- 注册表操作命令和自定义cmd窗口
- 夺命雷公狗---微信开发57----微网站之jquery_mobile之入门案例
- lhgDialog
- Android开发小记
- Java笔记(二)
- 用C写一个web服务器(一) 基础功能
- java学习笔记 --- java基础语法
- 没有在xml中引入 相关的配置文件
- 【JavaScript】设计模式-module模式及其改进
- Asp.Net MVC 中JS通过ajaxfileupload上传图片获取身份证姓名、生日、家庭住址等详细信息
- REST AND SOAP
- Java面试知识点之数据库篇(一)
- Redis——windows下如何连接Linux(centos7.x)虚拟机的Redis——【二】
- Luogu P5285 / LOJ3050 【[十二省联考2019]骗分过样例】
- Django学习笔记之数据库-数据库与模型
- windows下nodejs服务器的安装与配置