问题描述
你获得了一个据说是古代玛雅人制作的箱子。你非常想打开箱子看看里面有什么东西,但是不幸的是,正如所有故事里一样,神秘的箱子出现的时候总是会挂着神秘的锁。

这个锁上面看起来有  N  个数字,它们排成一排,并且每个数字都在  0  到  2 
之间。你发现你可以通过锁上的机关来交换相邻两个数字的顺序。比如,如果原来有  5  个数字  02120,在一次交换以后你就可以得到 
20120,01220,02210  或者  02102。

根据你所搜集的情报,这个锁在上面存在某连续四个数字是“2012”的时候会自动打开。现在,你需要计算一下,你至少需要进行多少次交换操作才能打开这把锁?

输入格式
输入数据的第一行有一个正整数  N。(4  ≤  N  ≤  13)  输入数据的第二行有  N  个数字  a1,a2, 
...,  aN  ,其中  ai  表示这个锁上面第  i  个数字的值,满足  0  ≤  ai  ≤  2。这些数字之间没有空格分隔。
输出格式

你只需要输出一个数字,即你至少需要的交换次数。如果无论如何都没有希望打开这把锁,输出  -1。
样例输入
5
02120

样例输出
1
对样例的解释
把前两个数字交换以后,锁上的数字是  20120,其中存在连续四个数字2,  0,  1, 
2,因此锁会打开。

思路: 对于开锁是当且仅当给定的的n个数字中出现2012,我们可以将这几个数字当成字符串输入 因为是求最小交换次数并且是每一次是一种新的状态所以我们很容易想到用BFS

将每一次交换后的新的状态和当前的交换次数加入队列,每一次判断是否达到开锁的状态;

注意: 因为每一次的交换可能会出现相同的状态 所以我们在交换之后要注意 首先:如果即将交换的=两个数字不同才进行交换,其次 如果交换后的状态已经出现过了就不用入队了

好了话不多说 直接上代码吧

#include<iostream>
#include<algorithm>
#include<queue>
#include<string>
#include<set> using namespace std;
typedef pair<string,int> P;
queue<P>Q;set<string>S;
int n;
bool goal(string str)//判断是否有达到开锁的条件
{
for(int i=;i+<str.size();i++)
if(str[i]==''&&str[i+]==''&&str[i+]==''&&str[i+]=='')
return true;
return false;
}
void BFS()
{
while(!Q.empty())
{
P q = Q.front();
Q.pop();
if(goal(q.first))//判断有没有达到可以开锁的状态
{
cout<<q.second<<endl;
return;
}
for(int i=;i<q.first.size()-;i++)
{
string str = q.first;
if(str[i]!=str[i+])
{
swap(str[i],str[i+]);
if(goal(str))
{
cout<<q.second+<<endl;
return;
}
if(S.count(str)!=)//剪枝 对于已经出现过的状态就不必再继续
{ //存入队列 例如22010 如果在之后的的交换中
S.insert(str); //再一次出现22010 则不需要再对它进行交换
P p; //S 是set类型 用于记录每一种情况有没有出现过
p.first = str; //没有则将其加入队列 加入集合
p.second = q.second+;
Q.push(p);
}
}
} }
cout<<"-1"<<endl;
}
int main()
{
string str;
P p;
while(cin>>n>>str)
{
S.clear();
while(!Q.empty())
Q.pop();
p.first = str;
p.second = ;
Q.push(p);
BFS();
} return ;
}

算法提高 密码锁 (BFS)的更多相关文章

  1. Java实现 蓝桥杯VIP 算法提高 密码锁

    算法提高 题目 2 密码锁 时间限制:1.0s 内存限制:1.0GB 问题描述 你获得了一个据说是古代玛雅人制作的箱子.你非常想打开箱子看看里面有什么东西,但是不幸的是,正如所有故事里一样,神秘的箱子 ...

  2. 蓝桥杯 算法提高 学霸的迷宫 经典BFS问题

      算法提高 学霸的迷宫   时间限制:1.0s   内存限制:256.0MB      问题描述 学霸抢走了大家的作业,班长为了帮同学们找回作业,决定去找学霸决斗.但学霸为了不要别人打扰,住在一个城 ...

  3. Java实现 蓝桥杯 算法提高 八数码(BFS)

    试题 算法提高 八数码 问题描述 RXY八数码 输入格式 输入两个33表格 第一个为目标表格 第二个为检索表格 输出格式 输出步数 样例输入 1 2 3 4 5 6 7 8 0 1 2 3 4 5 6 ...

  4. 算法笔记_107:蓝桥杯练习 算法提高 学霸的迷宫(Java)

    目录 1 问题描述 2 解决方案   1 问题描述 问题描述 学霸抢走了大家的作业,班长为了帮同学们找回作业,决定去找学霸决斗.但学霸为了不要别人打扰,住在一个城堡里,城堡外面是一个二维的格子迷宫,要 ...

  5. 蓝桥杯--算法提高 排列数 (简单dfs)

    算法提高 排列数   时间限制:1.0s   内存限制:256.0MB      问题描述 0.1.2三个数字的全排列有六种,按照字母序排列如下: 012.021.102.120.201.210 输入 ...

  6. Java实现 蓝桥杯 算法提高 学霸的迷宫

    算法提高 学霸的迷宫 时间限制:1.0s 内存限制:256.0MB 问题描述 学霸抢走了大家的作业,班长为了帮同学们找回作业,决定去找学霸决斗.但学霸为了不要别人打扰,住在一个城堡里,城堡外面是一个二 ...

  7. 蓝桥杯算法提高 P1001(大数乘法)

      算法提高 P1001   时间限制:1.0s   内存限制:256.0MB   当两个比较大的整数相乘时,可能会出现数据溢出的情形.为避免溢出,可以采用字符串的方法来实现两个大数之间的乘法. 具体 ...

  8. 机器学习实战 - 读书笔记(07) - 利用AdaBoost元算法提高分类性能

    前言 最近在看Peter Harrington写的"机器学习实战",这是我的学习笔记,这次是第7章 - 利用AdaBoost元算法提高分类性能. 核心思想 在使用某个特定的算法是, ...

  9. 算法提高 c++_ch02_01

    http://lx.lanqiao.org/problem.page?gpid=T237  算法提高 c++_ch02_01   时间限制:1.0s   内存限制:512.0MB      编写一个程 ...

随机推荐

  1. Directx11教程(49) stencil的应用-镜面反射

    原文:Directx11教程(49) stencil的应用-镜面反射      本教程中,我们利用stencil来实现一个镜面反射效果. 1.首先我们要在D3DClass中增加几个成员变量及函数. I ...

  2. 使用php simple html dom parser解析html标签

    转自:http://www.blhere.com/1243.html 使用php simple html dom parser解析html标签 用了一下 PHP Simple HTML DOM Par ...

  3. 【JZOJ4835】【GDOI2017模拟10.31】量化交易

    题目描述 数据范围 解法 贪心: 从左往右枚举,设枚举到元素为x,并维护一个堆: 设此时堆顶元素为y, 如果x大于y,那么x可以与y产生差价,立即将差价贡献给答案. 如果y之前已经和其他元素z产生过差 ...

  4. Extended Traffic

    题目链接 题意:有n个路口,m条通路,如果经过一条路则会得到(终点 - 起点)^3的权值,求从1点到其他点的最小权值,如果权值小于3或无法到达输出'?'. 题解:因为权值可能为负,所以用SPFA来解题 ...

  5. linux下安装使用MySQL 以及 python mysqldb 遇到的问题

    一.安装mysql sudo apt-get install mysql-client-core-5.5 然后会出现: ERROR 2002 (HY000): Can't connect to loc ...

  6. Code Force 429B Working out【递推dp】

    Summer is coming! It's time for Iahub and Iahubina to work out, as they both want to look hot at the ...

  7. c++:三

    C++:三   对于共享数据的保护,我们可以使用常量,在使用数据的同时也防止了数据被修改,即可有效的保护数据. 常对象   常对象必须在定义对象时就使用"const"关键字将指定对 ...

  8. IO NIO AIO及常用框架概述

    概述 nio 同步: 自己亲自出马持银行卡到银行取钱(使用同步IO时,Java自己处理IO读写). 异步: 委托一小弟拿银行卡到银行取钱,然后给你(使用异步IO时,Java将IO读写委托给OS处理,需 ...

  9. Redis源码解析:01简单动态字符串SDS

    Redis没有直接使用C字符串(以'\0'结尾的字符数组),而是构建了一种名为简单动态字符串( simple  dynamic  string, SDS)的抽象类型,并将SDS用作Redis的默认字符 ...

  10. epoll与fork

    使用epoll时,如果在调用epoll_create之后,调用了fork创建子进程,那么父子进程虽然有各自epoll实例的副本,但是在内核中,它们引用的是同一个实例.子进程向自己的epoll实例添加. ...