poj1473到处都是宝藏和 poj1772新围棋

37 篇文章 1 订阅

1.到处都是宝藏

问题描述:你有一张地图来让你寻找宝藏,但是沿着它给你的路线不一定是最近的方法,你要找到最近的方法并且求出它的最短距离和宝藏的位置,宝藏的位置以开始的坐标为原点,向右为x轴正方向,想上为y轴正方向来相对标注。

数据输入:

 解决思路:

根据地图所给的内容,这一串字符告诉我们代表一步一步的步骤,每一行代表一个地图,以句号为结束每一个地图的结束标志,例如3N代表向北走三格的距离,依次类推,直到碰到句号,一个地图就结束了,也就是找到了一个宝藏,但是这个距离有11格远的距离明显不是最近的距离,最近的距离就是宝藏的位置和开始的连线的长度,所以只要先按照地图找到宝藏,再根据两点之间直线最短求出最短距离即可,重点是代码部分如何来写,想要找到宝藏的坐标,那给用两个参数来代表x轴和y轴,每次操作一个字符串就对x或y进行加减操作,距离就是√x²+y²,显然代码要用到选择,根据不同的方向来对x,y操作

代码片段:

#include <stdio.h>             
#include <iostream>         
输入输出头文件;
#include <algorithm>
#include <string>
#include <math.h>             
要用到根号算法;
using namespace std;
const double t = sqrt(2.0);       定义t为根号2这个常数;
 
int main()
{
    string s;
    int icase = 1;              代表地图序号;
    while(cin >> s) {
        if(s == "END") {        end代表结束,如果遇到,即代表所有地图已经遍历完毕;
            break;
        }
        int num = 0;
        double x = 0, y = 0;
        for(int i = 0; i < (int)s.length()-1; ++i) {
            if(s[i] >= '0' && s[i] <= '9') {
                num = num*10+(s[i]-'0');     将字符串转化为数字;
            }
            else if(s[i] == ','){
                num = 0;
                continue;
            }
            else if(s[i] == 'N' && s[i+1] == 'E') {     
                x+=num/t, y+=num/t, i++;
            }
            else if(s[i] == 'N' && s[i+1] == 'W') {
                x-=num/t, y+=num/t, i++;
            }
            else if(s[i] == 'S' && s[i+1] == 'E') {
                x+=num/t, y-=num/t, i++;
            }
            else if(s[i] == 'S' && s[i+1] == 'W') {   这四个代表东南东北西南西北四个方向,横纵坐标都要除以t即根号2;
                x-=num/t, y-=num/t, i++;
            }
            else if(s[i] == 'N') {
                y+=num;
            }
            else if(s[i] == 'S') {
                y-=num;
            }
            else if(s[i] == 'E') {
                x+=num;
            }
            else if(s[i] == 'W') {     这四个只要对相应的横坐标或者纵坐标操作即可;
                x-=num;
            }
             
        }
        printf("Map #%d\n", icase++);      地图序号;
        printf("The treasure is located at (%.3lf,%.3lf).\n", x, y);    宝藏坐标;
        printf("The distance to the treasure is %.3lf.\n\n", sqrt(x*x+y*y));   最短距离;
    }  
 
    return 0;
}

提交已ac!

2.新围棋

问题描述:现在有一个下好的围棋,让你找到封闭点,即符合第一,封闭式路口必须是没有任何石头的路口。第二,任何边界的交叉点都不能是封闭的交叉点。第三,附近的四个交叉点(上、下、左、右)必须是封闭的交叉点或被黑色石头占据。如图

直接看图找封闭点太简单了,现在告诉你四行数字,分别代表每行,每列, 每条斜线上的黑石数量(从左到右,从上到下),每条斜线上(从左到右,从下到上),然后根据这四行数字来找到封闭点。

我的思路:想要根据这四行将黑棋的分布想出来可真是太难了,不如逆向思维,对每一个可能是封闭点的位置进行证实,如果满足四行数字的要求,有根据封闭点的规则,我们可以去掉四个角落的可能性,但是封闭的数量是未知的,所以对每一个有可能的位置一一证实,如果假设那个点是封闭点,但是不符合四行数字的要求,即假设失败,那个点就不是封闭点,直到最后全都证实完后,就可以求出全部的封闭点。

代码还未ac。

3.城堡问题(百练2815)

问题描述:如图是一个城堡的地形图。请你编写一个程序,计算城堡一共有多少个房间,最大的房间有多大。城堡被分割成m×n(m<=50,n<=50)个方块,每个方块可以有四面墙。

输入输出要求:
①第一行是两个整数,分别是南北向、东西向的方块数。
②在接下来的输入行里,每个方块用一个数字(0≤p≤50)描述。用一个数字表示方块周围的墙,1表示西墙,2表示北墙,4表示东墙,8表示南墙。
③每个方块用代表其周围墙的数字之和表示。城堡的内墙被计算两次,方块(1,1)的南墙同时也是方块(2,1)的北墙。
④输入的数据保证城堡至少有两个房间。

输入:

输出:

解题思路:给每个房间都标记数字,连在一起的房间就用同一个数字,,最后只要看有几种数字,每个数字的数量,就可以得到房间的数量和最大的房间个数。

代码:

#include<iostream>

#include<stack>

#include<cstring>

using namespace std;

int r,c;

int rooms[60][60];

int color[60][60];

int maxroomarea = 0,roomnum = 0;

int roomarea;

void dfs(int i,int k) {                     染色即给同一房间一个数字函数;

                if( color [i][k)              染过色的直接跳过;              

                              return;

                ++roomarea;

                 color[i][k] = roomnum;

                 if(  (rooms[i][k] & 1) ==  0)     dfs(i,k-1);         向西走;

                 if(  (rooms[i][k] & 2) ==  0)     dfs(i-,k);            向北走;

                  if(  (rooms[i][k] & 4) ==  0)     dfs(i,k+1);        向东走;

                   if(  (rooms[i][k] & 8) ==  0)     dfs(i+,k);         向南走;

int main()  {
           cin >> r >> c;

           for(  int i=1;i<=r;++i)

                     for( int k=1;k<=c;++k)

                                       cin>> rooms[i][k];         原始数据输入;

            memset(color,0,sizeof(color));                 全部赋值为0,变1的就代表遍历过;

            for( int i;i<=r;++i)

                        for( int k=1;k<=c;++k)  {

                                    if(!color[i][k])   {
                                             ++roomnum;          一个连接片完结,开始另一个连接片;

                                             roomarea =0;

                                             dfs(i,k);                  调用函数求得房间数最大值

                                              maxroomarea=max(roomarea, maxroomarea);   不断更新最大值

                                     }

                         }

cout << roomnum << endl;            输出房间数;

cout << maxroomarea<<endl;         输出房间数量最多的值

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值