Snail Trail[USACO]

已经不记得这个题目是什么了。

 

/*
ID: zhangyc1
LANG: C++
TASK: snail
*/
#include <string>
#include <cstring>
#include <cstdlib>
#include <cstdio>
#include <cmath>
using namespace std;
int N, B, nMaxSetp = 0, nCurStep = 0;

bool arrIsBar[120][120], arrVisited[120][120];
int arrDirectionX[4] = {0, 1, 0, -1};//右下左上
int arrDirectionY[4] = {1, 0, -1, 0};

void prepairData()
{
    memset(arrIsBar, 0, false);
    memset(arrVisited, 0, false);
    scanf("%d%d", &N, &B);
    char    ch[5];
    for (int i = 0; i < B; i++)
    {
        scanf ("%s", &ch);
        arrIsBar[atoi (ch + 1) - 1][ch[0] - 'A'] = true;
    }
}

void dfs(int i, int j, int d)
{// i-行, j-列, d-方向:0右,1下,2左,3上
    int nNewI, nNewJ;
    bool bEnd = false, bTurnLeft = false, bTurnRight = false;
    bool arrTempVisited[120][120];
    int nLeftX, nLeftY, nRightX, nRightY;
    for (nNewI = i, nNewJ = j ; nNewI >= 0 && nNewI < N && nNewJ >= 0 && nNewJ < N && !arrIsBar[nNewI][nNewJ];nNewI += arrDirectionX[d], nNewJ += arrDirectionY[d])
    {
        if (arrVisited[nNewI][nNewJ])
        {
            bEnd = true;
            break;
        }
        arrVisited[nNewI][nNewJ] = true;
    }
    if (!bEnd)//判断是否可以转动
    {
        nLeftX = nNewI - arrDirectionX[d] + arrDirectionX[(d + 3)%4], nLeftY = nNewJ - arrDirectionY[d] + arrDirectionY[(d + 3)%4];
        nRightX = nNewI - arrDirectionX[d] + arrDirectionX[(d + 1)%4], nRightY = nNewJ - arrDirectionY[d] + arrDirectionY[(d + 1)%4];
        bTurnLeft = nLeftX >= 0 && nLeftX < N && nLeftY >= 0 && nLeftY < N && !arrIsBar[nLeftX][nLeftY] && !arrVisited[nLeftX][nLeftY];
        bTurnRight = nRightX >= 0 && nRightX < N && nRightY >= 0 && nRightY < N && !arrIsBar[nRightX][nRightY] && !arrVisited[nRightX][nRightY];
        bEnd = !(bTurnLeft || bTurnRight);
    }

    nCurStep += abs(nNewI - i + nNewJ - j);
    if (bEnd)
    {
        if (nCurStep > nMaxSetp)
            nMaxSetp = nCurStep;
    }
    else
    {
        int nOldStep = nCurStep;
        memcpy(arrTempVisited, arrVisited, sizeof(arrVisited));
        if (bTurnLeft)
        {
            dfs(nLeftX, nLeftY, (d + 3) % 4);
            memcpy(arrVisited, arrTempVisited, sizeof(arrVisited));
            nCurStep = nOldStep;
        }
        if (bTurnRight)
            dfs(nRightX, nRightY, (d + 1) % 4);
    }
}

void process()
{
    nCurStep = 0;
    dfs(0, 0, 1);//初始向下

    nCurStep = 0;
    memset(arrVisited, 0, sizeof(arrVisited));
    dfs(0, 0, 0);//初始向右
    printf("%d\n", nMaxSetp);
}

int main(){
    FILE *streamIn = freopen("snail.in","r",stdin);
    FILE *streamOut = freopen("snail.out","w",stdout);
    prepairData();
    process();
    fclose(streamIn);
    fclose(streamOut);
    return 0;
}

 

转载于:https://www.cnblogs.com/doublemystery/archive/2013/05/09/3068678.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值