hiho一下第114周《Image Encryption》 - 最小表示法

来源:互联网 发布:c语言入门程序代码 编辑:程序博客网 时间:2024/06/05 08:12

http://hihocoder.com/contest/hiho114/problem/1


官方解析:http://hihocoder.com/discuss/question/3663


能想到最小表示法的话就很好做了

奇数直接暴力旋转3次取最优

偶数递归分解,得到最后子矩阵后,再暴力旋转三次取最优


复杂度也就那样吧。。刚开始直接每次复制新矩阵。。TLE。。。


后面直接传一个引用从头用到尾得了。(传引用+起点终点坐标)


旋转全矩阵和旋转四个子块都是暴力的旋转。


最后跑了1300ms

#include<iostream>#include<cstdio>#include<algorithm>using namespace std;struct mat{    int mp[101][101];};bool cmp(const mat&a,const mat&b,int x1,int y1,int x2,int y2 ){    for (int i=x1; i<=x2; i++)    for (int j=y1; j<=y2; j++)            if (a.mp[i][j]!=b.mp[i][j])                return     (a.mp[i][j]<b.mp[i][j]);    return false;}void rotate(mat &m,int n,int x1,int y1,int x2,int y2){    mat tmp;    for (int i=x1; i<=x2; i++)    for (int j=y1; j<=y2; j++)     tmp.mp[j-y1+1+x1-1][x2-i+1+y1-1]=m.mp[i][j];    for (int i=x1; i<=x2; i++)      for (int j=y1; j<=y2; j++)      m.mp[i][j]=tmp.mp[i][j];}void rotate_block(mat &m,int n,int x1,int y1,int x2,int y2){    int n1=(x2-x1+1)/2;    int n2=(y2-y1+1)/2;    for (int i=x1; i<n1+x1; i++)        for (int j=y1; j<n2+y1; j++)            swap(m.mp[i][j],m.mp[i+n1][j]),                 swap(m.mp[i+n1][j],m.mp[i+n1][j+n2]),                 swap(m.mp[i+n1][j+n2],m.mp[i][j+n2]);}void dfs(mat& m,int n,int x1,int y1,int x2,int y2){    if (n%2)    {         mat tmp=m;        for (int i=1; i<=3; i++)        {            rotate(tmp,n,x1,y1,x2,y2);            if (cmp(tmp,m ,x1,y1,x2,y2)==true) m=tmp;        }     }    else    {        int mx=(x1+x2)/2;        int my=(y1+y2)/2;        dfs(m,n/2,x1,y1,mx,my);        dfs(m,n/2,mx+1,y1,x2,my);        dfs(m,n/2,x1,my+1,mx,y2);        dfs(m,n/2,mx+1,my+1,x2,y2);         mat tmp=m;        for (int i=1; i<=3; i++)        {            rotate_block(tmp,n,x1,y1,x2,y2);            if (cmp(tmp,m,x1,y1,x2,y2 ))                m=tmp;        }     }}int main(){    int n;    int t;    cin>>t;    while(t--)    {        scanf("%d",&n);        mat m1,m2;        for (int i=1; i<=n; i++)    for (int j=1; j<=n; j++)  scanf("%d",&m1.mp[i][j]);        for (int i=1; i<=n; i++)    for (int j=1; j<=n; j++)  scanf("%d",&m2.mp[i][j]);        dfs(m1,n,1,1,n,n);        dfs(m2,n,1,1,n,n);        int flag=0;        for (int i=1; i<=n; i++)    for (int j=1; j<=n; j++) if (m1.mp[i][j]!=m2.mp[i][j]) flag=1;        if (flag) printf("No\n");        else  printf("Yes\n");    }    return 0;}


0 0
原创粉丝点击