前言
今天和室友一起玩开心拼一拼的时候,一不小心我俩一起卡关了,于是本蒟蒻一怒之下跑去写了个攻略形的外挂(显示出过关的详细步骤),如果有卡关的可以下载exe文件取用该攻略
exe文件链接
链接:https://pan.baidu.com/s/1l09rLR57OFe9SW1FCrovCg
提取码:0jh5
使用说明
使用的图片如下:
输入的内容如下:
9
蓝 浅蓝 草绿 浅蓝
蓝 红 草绿 紫
灰 紫 蓝 蓝
红 粉 橙 绿
灰 绿 粉 红
橙 绿 绿 草绿
草绿 灰 紫 红
紫 灰 粉 橙
橙 浅蓝 浅蓝 粉
2
说明:需要按照提示输入当前关卡的有颜色的试管数量、每个试管的颜色、空试管的数量
注意:我玩的版本将试管分为了四块,不知道会不会有其余版本的,该攻略仅适用于分为四块颜色的试管
代码
#define _CRT_SECURE_NO_WARNINGS
#include<iostream>
#include<stack>
#include<algorithm>
#include<map>
#include<vector>
#include<queue>
using namespace std;
const int maxn = 1000;
stack<int>st[maxn];
stack<int>tmp;
int num[maxn];
int book[maxn];
map<string, int>mp;
int n, m, tot, cnt,wc;
vector<int>path;
int win() {
int res = 0;
int flag = 0;
memset(book, 0, sizeof(book));
for (int i = 1; i <= tot; i++) {
flag = 0;
if (st[i].size() < 4) {
continue;//不满,肯定不符合
}
while (!st[i].empty()) {
int fr = st[i].top();
tmp.push(fr);
st[i].pop();
if (!st[i].empty() && fr != st[i].top()) {
flag = 1;//不满足
}
}
while (!tmp.empty()) {
st[i].push(tmp.top());
tmp.pop();
}
if (!flag)book[i] = 1, res++;
}
return res;
}
void dfs(int last, int to) {
int ans = win();
if (ans == n) {
for (int i = 0; i + 1 < path.size(); i += 2) {
printf("将第%d个试管倒入%d\n", path[i], path[i + 1]);
}
printf("已完成\n");
wc = 1;
return;//已完成
}
if (wc)return;
for (int i = 1; i <= tot; i++) {
if (!st[i].size())continue;//是空的
if (book[i])continue;//当前已完成
int si = st[i].size();
int fr = st[i].top();
st[i].pop();
int ne = 1;
while (!st[i].empty() && st[i].top() == fr) {//算出可以移动的数量
ne++;
st[i].pop();
}
int same = 0;
if (ne == si) {//一个试管,同色,标记一下
same = 1;
}
for (int j = 1; j <= tot; j++) {
if (last == j && to == i) {//和上一次操作是反操作
continue;
}
if (i == j)continue;//是同一个
if (num[j] == 4)continue;//满了
if (same && num[j] == 0)continue;//没必要把同色试管倒进空试管
int to;
if (!st[j].empty()) {//非空,判断是否能倒
to = st[j].top();
}
else {//空的,可以倒
to = fr;
}
if (fr == to) {//同色,可以倒
int nu = 4 - num[j];
if (nu < ne)continue;//要去的不够当前要倒的,没必要倒
for (int k = 1; k <= ne; k++) {
st[j].push(fr);
}
num[j] += ne;
num[i] -= ne;
path.push_back(i);
path.push_back(j);
dfs(i, j);
path.pop_back();//回溯
path.pop_back();
num[j] -= ne;
num[i] += ne;
for (int k = 1; k <= ne; k++) {
st[j].pop();
}
}
else {
continue;//继续下一个
}
}
for (int k = 1; k <= ne; k++) {//回溯
st[i].push(fr);
}
}
}
void init() {
memset(num, 0, sizeof(num));
path.clear();
for (int i = 1; i < maxn; i++) {
while (!st[i].empty())st[i].pop();
}
mp.clear();
wc = 0;
}
int main() {
cnt = 0;
string col;
while (1) {
init();
printf("请输入有颜色的试管数量:");
scanf("%d", &n);
for (int i = 1; i <= n; i++) {
num[i] = 4;
printf("请从下往上输入第%d个试管的四个颜色:", i);
for (int j = 1; j <= 4; j++) {
cin >> col;
if (mp.find(col) == mp.end()) {
mp[col] = ++cnt;
}
st[i].push(mp[col]);
}
}
printf("请输入空试管数量:");
scanf("%d", &m);
tot = n + m;
dfs(-1, -1);
}
return 0;
}
后记
目前我测试的关卡没有出现BUG,不知道会不会有其余的关卡出现BUG,如果有还请各位大佬评论区指出QAQ
——蒟蒻的第十篇博客
(翻了翻之前的博客,发现最后一篇是半年前我刚好在学爆搜的时候??)
其他碎碎念
暴力出奇迹,爆搜出攻略!
中秋快乐(▽)
2021-9-20 23:49