zoukankan      html  css  js  c++  java
  • CF51A Cheaterius's Problem 题解

    CF51A Cheaterius's Problem 题解

    题目分析

    这道题是一个很不错的锻炼代码能力的题,主要思路是模拟。

    每一张牌都是 (2 imes2) 的大小。而且如果两张牌通过旋转能重合就是同一张牌,我们可以模拟这一过程。

    因为题目中是依次输入每一张牌,所以我们可以采用边读边操作的方法。此题的读入操作是个大工程。

    为了方便读入,我们可以用 char 形式的字符读入,读入之后转成 int 类型。然后把 (a,b,c,d)(f) 数组中的数相比较。如果它们是相同的牌,则让总牌数+1;否则就把这四个数存入 (f) 数组,代表多了一张不同的牌。

    存储每一张牌,我们可以采用三维数组 f[i][j][k] 来存储,其中 (k) 表示不同的牌的张数。 我们设左上角的牌为 (a) ,右上角的牌为 (b) ,左下角为 (c) ,右下角为 (d) 。则有:

    读入操作代码:

    char x;
    cin>>x>>x; //读入星号
    cin>>ch1>>ch2;
    cin>>ch3>>ch4;
    int a=ch1-'0',b=ch2-'0'; // char 转 int 
    int c=ch3-'0',d=ch4-'0';
    f[1][1][1]=a; //存入 f 数组
    f[1][2][1]=b;
    f[2][1][1]=c;
    f[2][2][1]=d;
    

    核心部分是枚举出所有是一张牌的情况。我们可以依次旋转90度枚举即可。操作过程如下图所示:

    旋转后的所有可能情况

    代码表示所有可能情况:

    if(a==f[1][1][j] && b==f[1][2][j] && c==f[2][1][j] && d==f[2][2][j])
    if(c==f[1][1][j] && a==f[1][2][j] && d==f[2][1][j] && b==f[2][2][j])
    if(d==f[1][1][j] && c==f[1][2][j] && b==f[2][1][j] && a==f[2][2][j])
    if(b==f[1][1][j] && d==f[1][2][j] && a==f[2][1][j] && c==f[2][2][j])
    

    最后输出 (f) 数组中的 (k) 即可。

    代码

    #include<iostream>
    #include<cstdio>
    using namespace std;
    int f[3][3][1003];
    int main()
    {
    	int n;
    	char ch1,ch2,ch3,ch4;
    	
    	//下面单独读入第一组数据,因为第一组数据上面没有星号
    	cin>>n;
    	cin>>ch1>>ch2;
    	cin>>ch3>>ch4;
    	f[1][1][1]=ch1-'0'; // char 转 int 存入
    	f[1][2][1]=ch2-'0';
    	f[2][1][1]=ch3-'0';
    	f[2][2][1]=ch4-'0';
    	
    	int k=1; // k 代表不同的牌的张数 
    	for(int i=2;i<=n;++i) // 从第2张牌继续读入 
    	{
    		bool ok=0; //临时 bool 数组,用来判断两张牌是不是相同的 
    		char x;
    		cin>>x>>x;
    		cin>>ch1>>ch2;
    		cin>>ch3>>ch4;
    		int a=ch1-'0';
    		int b=ch2-'0';
    		int c=ch3-'0';
    		int d=ch4-'0';
    		
    		for(int j=1;j<=k;++j) //在每张不同的牌之间枚举,看看此牌和之前的牌是不是相同 
    		{
    			if(a==f[1][1][j] && b==f[1][2][j] && c==f[2][1][j] && d==f[2][2][j])
    			{
    				ok=1; //完全相同的情况
    				break;//如果和之前的牌相同,则可以跳出循环,继续读入下一组数据
    			}
    			if(c==f[1][1][j] && a==f[1][2][j] && d==f[2][1][j] && b==f[2][2][j])
    			{
    				ok=1; //顺时针旋转90度
    				break;//同上
    			}
    			if(d==f[1][1][j] && c==f[1][2][j] && b==f[2][1][j] && a==f[2][2][j])
    			{
    				ok=1;//顺时针旋转180度
    				break;//同上
    			}
    			if(b==f[1][1][j] && d==f[1][2][j] && a==f[2][1][j] && c==f[2][2][j])
    			{
    				ok=1;//顺时针旋转270度
    				break;//同上
    			}
    		}
    		if(ok==0) //如果这张牌和前面的各不相同,那么把这张牌存入 f 数组 
    		{
    			f[1][1][++k]=ch1-'0';
    			f[1][2][k]=ch2-'0';
    			f[2][1][k]=ch3-'0';
    			f[2][2][k]=ch4-'0';
    		}
    	}
    	printf("%d
    ",k); //最后输出不同的牌的张数 
    }
    

    提交记录

    题解到此结束,希望大家看完思路自己模拟着打一遍,杜绝抄袭哦~

  • 相关阅读:
    3.17爸爸要回去了(之十一)
    爸爸丢了 (2013.3.10,确诊五天后,之十)
    Polyline转Polygon
    将一个应用程序添加做成windows服务
    找个输入IPoint在某个FeatureClass上距离最近的要素
    线程间操作无效: 从不是创建控件“label4”的线程访问它。
    删除文件夹下的文件和文件夹
    int组成时间值
    CRONTAB
    NFS
  • 原文地址:https://www.cnblogs.com/EdisonBa/p/13619397.html
Copyright © 2011-2022 走看看