poj 1099 Square Ice

Description

Square Ice is a two-dimensional arrangement of water molecules H2O, with oxygen at the vertices of a square lattice and one hydrogen atom between each pair of adjacent oxygen atoms. The hydrogen atoms must stick out on the left and right sides but are not allowed to stick out the top or bottom. One 5 x 5 example is shown below. 


Note that each hydrogen atom is attached to exactly one of its neighboring oxygen atoms and each oxygen atom is attached to two of its neighboring hydrogen atoms. (Recall that one water molecule is a unit of one O linked to two H's.) 

It turns out we can encode a square ice pattern with what is known as an alternating sign matrix (ASM): horizontal molecules are encoded as 1, vertical molecules are encoded as -1 and all other molecules are encoded as 0. So, the above pattern would be encoded as: 


An ASM is a square matrix with entries 0, 1 and -1, where the sum of each row and column is 1 and the non-zero entries in each row and in each column must alternate in sign. (It turns out there is a one-to-one correspondence between ASM's and square ice patterns!) 

Your job is to display the square ice pattern, in the same format as the example above, for a given ASM. Use dashes (-) for horizontal attachments and vertical bars (|) for vertical attachments. The pattern should be surrounded with a border of asterisks (*), be left justified and there should be exactly one character between neighboring hydrogen atoms (H) and oxygen atoms (O): either a space, a dash or a vertical bar.

Input

Input consists of multiple cases. Each case consists of a positive integer m (<= 11) on a line followed by m lines giving the entries of an ASM. Each line gives a row of the ASM with entries separated by a single space. The end of input is indicated by a line containing m = 0.

Output

For each case, print the case number (starting from 1), in the format shown in the Sample Output, followed by a blank line, followed by the corresponding square ice pattern in the format described above. Separate the output of different cases by a blank line.

Sample Input

2
0 1
1 0
4
0 1 0 0
1 -1 0 1
0 0 1 0
0 1 0 0
0

Sample Output

Case 1:

***********
*H-O H-O-H*
*  |      *
*  H   H  *
*      |  *
*H-O-H O-H*
***********

Case 2:

*******************
*H-O H-O-H O-H O-H*
*  |       |   |  *
*  H   H   H   H  *
*      |          *
*H-O-H O H-O H-O-H*
*      |   |      *
*  H   H   H   H  *
*  |           |  *
*H-O H-O H-O-H O-H*
*      |          *
*  H   H   H   H  *
*  |       |   |  *
*H-O H-O-H O-H O-H*
*******************
题意:由一堆水分子组成的正方形,可以用化学式写成也可以用0,1,-1构成的矩阵写成,数字矩阵具有每行每列上的数字加起来等于1的特点,1代表横着放,-1代表竖着放,0则不确定(有4种情况)。
要求根据给出的数字矩阵写出化学式。
 
 
思路:首先观察到化学式中氧原子的位置固定(每行n个,共n行)。1,-1的化学式固定。所以先计算氧原子的坐标,在计算-1,1情况下氢原子的坐标,最后根据已有位置计算0情况下的氢原子的坐标。
由于每行的数字加起来式1,所以共有5+(n-1)*3+n+1=4*n+3列,1+(n-1)*3+n+1=4*n-1行。氧原子的横纵坐标每次增加4。0号氢原子的坐标按照有空位则放的原则放(上下只能放一边)。
 
 
反思:关键算是找规律吧,看到氧原子分布的规律和数字0的氢原子的规律,快速分析,棋盘问题要注意横纵坐标y代表纵坐标,即列。注意PE。
AC代码:
//
//  main.cpp
//  poj1099
//
//  Created by Charles on 2017/7/9.
//  Copyright © 2017年 Charles. All rights reserved.
//

#include <iostream>
#include <algorithm>
#include <string>
#include <cstring>
using namespace std;
int n,map[13][13];
char ans[60][60];
int main(int argc, const char * argv[]) {
    int c=1;
    while(cin>>n && n){
        for(int i=0;i<n;++i)
            for(int j=0;j<n;++j)
                cin>>map[i][j];
        cout<<"Case "<<c++<<":"<<endl<<endl;
        memset(ans,' ',sizeof(ans));
        for(int i=0;i<4*n+3;++i)
            ans[0][i]=ans[4*n-2][i]='*';
        for(int i=0;i<4*n-1;++i)
            ans[i][0]=ans[i][4*n+2]='*';
        int x=-3,y;
        for(int i=0;i<n;++i){
            x+=4;   y=-1;
            for(int j=0;j<n;++j){
                y+=4;
                ans[x][y]='O';
                if(map[i][j]==1){
                    ans[x][y-2]=ans[x][y+2]='H';
                    ans[x][y-1]=ans[x][y+1]='-';
                }
                if(map[i][j]==-1){
                    ans[x-2][y]=ans[x+2][y]='H';
                    ans[x-1][y]=ans[x+1][y]='|';
                }
            }
        }
        x=-3;
        for(int i=0;i<n;++i){
            x+=4;   y=-1;
            for(int j=0;j<n;++j){
                y+=4;
                if(map[i][j]==0){
                    if(x-2>0 && ans[x-2][y]==' '){
                        ans[x-2][y]='H';
                        ans[x-1][y]='|';
                    }
                    else{
                        ans[x+2][y]='H';
                        ans[x+1][y]='|';
                    }
                    if(y-2>0 && ans[x][y-2]==' '){
                        ans[x][y-2]='H';
                        ans[x][y-1]='-';
                    }
                    else{
                        ans[x][y+2]='H';
                        ans[x][y+1]='-';
                    }
                }
            }
        }
        for(int i=0;i<4*n-1;++i){
            for(int j=0;j<4*n+3;++j)
                cout<<ans[i][j];
            cout<<endl;
        }
        cout<<endl;
    }
    return 0;
}


 
 
 
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值