码迷,mamicode.com
首页 > 其他好文 > 详细

codevs 1225:八数码难题【双向广搜】

时间:2017-05-29 22:23:30      阅读:278      评论:0      收藏:0      [点我收藏+]

标签:div   problem   swap   images   main   break   str   clu   namespace   

这里是传送门

技术分享

这道题用普通BFS是可以做的,但是很明显没得过,效率太低了。效率更高的算法A*和双向广搜都可取,这写一下双向广搜的。

注意题目中的判重很重要,可以转化成九位数用hash来解决这个问题。

#include <set>
#include <string>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
#define oo 0x7f7f7f7f
#define str string
#define put(x) printf("%d\n", x)
#define cln(x) memset(x, 0, sizeof(x))
using namespace std;

str st;
str s[100005][2];
int h[2];
int t[2];
int b[100005][2];
set <str> hash[2];

void check(int x)
{
    if ( hash[1-x].count( s[t[x]][x] ) )
    {
        for (int i = 1; i <= t[1-x]; i++)
            if ( s[i][1-x] == s[t[x]][x] )
            {
                put(b[i][1-x]+b[t[x]][x]);
                break;
            }
        exit(0);
    }
}

str get( str s, int i )
{
    str x = s;
    int p = s.find(0);
    if ( i == 1 )
    {
        if ( p < 3 ) return "-1";
        swap( t[p], t[p-3] );
        return x;
    }
    if ( i == 2 )
    {
        if ( p == 0 || p == 3 || p == 6 ) return "-1";
        swap( t[p], t[p-1] );
        return x;
    }
    if ( i == 3 )
    {
        if ( p > 5 ) return "-1";
        swap( t[p], t[p+3] );
        return x;
    }
    if ( i == 4 )
    {
        if ( p == 2 || p == 5 || p == 8 ) return "-1";
        swap( t[p], t[p+1] );
        return x;
    }
}

void go(int x)
{
    h[x]++;
    str ss = s[h[x]][x];
    int c = b[h[x]][x] + 1;
    for ( int i = 1; i <= 4; i ++ )
    {
        str sss = get( ss, i );
        if ( sss == "-1" || hash[x].count(sss) ) continue;
        else
        {
            hash[x].insert(sss);
            t[x]++;
            b[t[x]][x] = c;
            s[t[x]][x] = sss;
            check(x);
        } 
    }
}

void Double_BFS()
{
    h[0] = h[1] = 0;
    t[0] = t[1] = 1;
    s[1][0] = st;
    s[1][1] = "123804765";
    while( h[0] < t[0] && h[1] < t[1] )
    {
        if (t[0] < t[1])
            go(0);
        else
            go(1);
    }
    
}

int main()
{
    cin >> st;
    Double_BFS();
    return 0;
}

 

codevs 1225:八数码难题【双向广搜】

标签:div   problem   swap   images   main   break   str   clu   namespace   

原文地址:http://www.cnblogs.com/GuanHuaEdison/p/6919140.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!