P2129 L 国的战斗续之多路出击

一道很有意思,但是其实不难的题。
跟上题很像,也是给我们递推式,找转移矩阵即可(比较好找,一下找对力)。
然后稍微想想就知道用结合律搞定。不过,这里尝试学习了一下矩阵乘法重载运算符,真的很好用(不然太浪费了,也不好看)

#include <bits/stdc++.h>
#define ll long long
#define re register
using namespace std;
const int N=500000+5, INF=0x3f3f3f3f;
int n,m;
char c;
struct Matrix{
	int a[4][4],l,r;
	Matrix(){memset(a,0,sizeof(a));}
	Matrix operator * (Matrix &tmp){
		Matrix c;c.l=l;c.r=tmp.r;
		for(int i=1;i<=c.l;i++)
			for(int j=1;j<=c.r;j++)
				for(int k=1;k<=r;k++)
					c.a[i][j]+=a[i][k]*tmp.a[k][j];
		return c;
	}
}x,y,p,b[N],mul;
struct data{
	char opt;int q1,q2;
}d[N];
int main(){
	x.l=x.r=3;x.a[1][1]=-1;x.a[2][2]=x.a[3][3]=1;
	y.l=y.r=3;y.a[2][2]=-1;y.a[1][1]=y.a[3][3]=1;
	p.l=p.r=3;p.a[1][1]=p.a[2][2]=p.a[3][3]=1;
	mul.l=mul.r=3;mul.a[1][1]=mul.a[2][2]=mul.a[3][3]=1;
	cin>>n>>m;
	for(int i=1;i<=n;i++){
		int x2,y2;cin>>x2>>y2;
		b[i].l=1;b[i].r=3;
		b[i].a[1][1]=x2;b[i].a[1][2]=y2;b[i].a[1][3]=1;
	}
	for(int i=1;i<=m;i++){
		cin>>d[i].opt;
		if(d[i].opt=='m')cin>>d[i].q1>>d[i].q2;
	}
	for(int i=m;i>=1;i--){
		c=d[i].opt;
		if(c=='x')mul=mul*x;
		else if(c=='y')mul=mul*y;
		else{
			p.a[3][1]=d[i].q1;p.a[3][2]=d[i].q2;
			mul=mul*p;
		}
	}
	for(int i=1;i<=n;i++){
		b[i]=b[i]*mul;
		cout<<b[i].a[1][1]<<' '<<b[i].a[1][2]<<endl;
	}
	return 0;
}
posted @ 2023-07-14 21:48  LsmQwQ  阅读(18)  评论(0)    收藏  举报