SDUT 周赛 2495 The Clocks DFS

http://acm.sdut.edu.cn/sdutoj/problem.php?action=showproblem&problemid=2495

题意:

给定一个3*3的矩阵,矩阵里面的数字的取值为3,6,9,12 。我们有9中操作,可以使举证中一些数字+3   ,问通过这九种操作我们能够用最少的操作数的序列,使得矩阵中的数字全部变成12.如果存在相同的则取字典序最小的。

思路:

才开始脑子转不过来,不知道怎么搜。。最后想了想,数字是以3的倍数增加的,每操作3次对应的数字又会回到原来的状态。所以我们只要枚举每种操作的次数。每种操作可以取0,1,2,3次这样的时间复杂度就是O(4^9)次方了。注意要对数字对12取余。

#include <iostream>

#include <cstdio>

#include <cstdlib>

#include <cstring>

#include <algorithm>

#include <cmath>

#include <queue>

#include <stack>

#include <set>

#include <map>

#include <string>



#define CL(a,num) memset((a),(num),sizeof(a))

#define iabs(x)  ((x) > 0 ? (x) : -(x))

#define Min(a,b) (a) > (b)? (b):(a)

#define Max(a,b) (a) > (b)? (a):(b)



#define ll __int64

#define inf 0x7f7f7f7f

#define MOD 1073741824

#define lc l,m,rt<<1

#define rc m + 1,r,rt<<1|1

#define pi acos(-1.0)

#define test puts("<------------------->")

#define maxn 100007

#define M 500007

#define N 10007

#define K 1007

using namespace std;

//freopen("din.txt","r",stdin);



int mk[10][5] = {

    {0,0,0,0,0},

    {1,2,4,5,0},

    {1,2,3,0,0},

    {2,3,5,6,0},

    {1,4,7,0,0},

    {2,4,5,6,8},

    {3,6,9,0,0},

    {4,5,7,8,0},

    {7,8,9,0,0},

    {5,6,8,9,0}

};

int ans[30],tmp[30];

int ansL;

int a[15];

int len;



bool isok()

{

    int i;

    for (i = 1; i <= 9; ++i)

    {

        if (a[i] != 0) return false;

    }

    return true;

}

void dfs(int pos)

{

    int i,j;

    for (i = 1; i <= 9; ++i) a[i] %= 12;

    if (isok())

    {

        if (ansL > len)

        {

            ansL = len;

            for (i = 0; i < len; ++i)

            ans[i] = tmp[i];

        }

        else if (ansL == len)

        {

            for (i = 0; i < len; ++i)

            {

                if (ans[i] > tmp[i]) break;

            }

            if (i < len)

            {

                for (i = 0; i < len; ++i) ans[i] = tmp[i];

            }

        }

        return;

    }

    else

    {

        if (pos > 9) return;

        for (i = 0; i <= 3; ++i)

        {

            for (j = 0; j < 5; ++j)

            a[mk[pos][j]] += 3*i;

            for (j = 0; j < i; ++j) tmp[len++] = pos;

            dfs(pos + 1);

            for (j = 0; j < i; ++j) len--;

            for (j = 0; j < 5; ++j)

            a[mk[pos][j]] -= 3*i;

        }

    }

}

int main()

{

    //freopen("din.txt","r",stdin);

    int i;

    while (~scanf("%d",&a[1]))

    {

        for (i = 2; i <= 9; ++i) scanf("%d",&a[i]);

        CL(ans,0); CL(tmp,0);

        ansL = inf; len = 0;

        dfs(1);



        for (i = 0; i < ansL - 1; ++i)

        printf("%d ",ans[i]);

        printf("%d\n",ans[i]);

    }

}

  

你可能感兴趣的:(Lock)