池の左側にアマガエルが、右側にヒキガエルが3匹ずつ並んでいる。 このカエルのいる場所をそっくり入れ替えてほしい。 カエルは前に飛ぶことしかできないが、1匹だけなら前にいるカエルを飛び越すことができる。 また、1枚の葉に同時に2匹以上のカエルが乗ることはできない。 さて、すべてのカエルを入れ替えるにはどうすればよいだろうか? カエルの引越し : クイズ&パズルの部屋「Quizzical Days.」
using System;
using System.Collections.Generic;
using System.Linq;
class Program
{
private enum MasuDef
{
Kuuhaku = 0,
Ama = 1,
Hiki = 2
}
private struct JyoutaiDef
{
internal MasuDef[] MasuArr;
internal List<MasuDef[]> Log;
}
static void Main()
{
var stk = new Stack<JyoutaiDef>();
JyoutaiDef WillPush;
WillPush.MasuArr = new MasuDef[] {
MasuDef.Ama, MasuDef.Ama,MasuDef.Ama,
MasuDef.Kuuhaku,
MasuDef.Hiki,MasuDef.Hiki,MasuDef.Hiki};
WillPush.Log = new List<MasuDef[]>() { WillPush.MasuArr };
stk.Push(WillPush);
int MaxLevel = (6 + 5 + 4) * 2;
int AnswerCnt = 0;
while (stk.Count > 0) {
JyoutaiDef Popped = stk.Pop();
if (MaxLevel < Popped.Log.Count) continue;
MasuDef[] AnswerArr = new MasuDef[] {
MasuDef.Hiki, MasuDef.Hiki,MasuDef.Hiki,
MasuDef.Kuuhaku,
MasuDef.Ama,MasuDef.Ama,MasuDef.Ama};
if (Popped.MasuArr.SequenceEqual(AnswerArr)) {
Console.WriteLine("解{0}を発見しました。", ++AnswerCnt);
PrintLog(Popped.Log);
if (MaxLevel > Popped.Log.Count)
MaxLevel = Popped.Log.Count;
continue;
}
int IndZero = Array.IndexOf<MasuDef>(Popped.MasuArr, MasuDef.Kuuhaku);
Action<int> PushSyori = (IndChanged) =>
{
WillPush.MasuArr = (MasuDef[])Popped.MasuArr.Clone();
WillPush.MasuArr[IndZero] = Popped.MasuArr[IndChanged];
WillPush.MasuArr[IndChanged] = 0;
WillPush.Log = new List<MasuDef[]>(Popped.Log);
WillPush.Log.Add(WillPush.MasuArr);
stk.Push(WillPush);
};
//空白の1つ左
if (1 <= IndZero && Popped.MasuArr[IndZero - 1] == MasuDef.Ama) {
PushSyori(IndZero - 1);
}
//空白の2つ左
if (2 <= IndZero && Popped.MasuArr[IndZero - 2] == MasuDef.Ama) {
PushSyori(IndZero - 2);
}
int UB = Popped.MasuArr.GetUpperBound(0);
//空白の1つ右
if (IndZero <= UB - 1 && Popped.MasuArr[IndZero + 1] == MasuDef.Hiki) {
PushSyori(IndZero + 1);
}
//空白の2つ右
if (IndZero <= UB - 2 && Popped.MasuArr[IndZero + 2] == MasuDef.Hiki) {
PushSyori(IndZero + 2);
}
}
}
static void PrintLog(List<MasuDef[]> pLog)
{
int Level = 0;
foreach (MasuDef[] AnyMasuDefineArr in pLog) {
Console.Write("LV{0,2}=", ++Level);
foreach (MasuDef AnyMasuDefine in AnyMasuDefineArr) {
if (AnyMasuDefine == MasuDef.Ama) Console.Write("アマ,");
if (AnyMasuDefine == MasuDef.Kuuhaku) Console.Write("空白,");
if (AnyMasuDefine == MasuDef.Hiki) Console.Write("ヒキ,");
}
Console.WriteLine();
}
}
}
解1を発見しました。 LV 1=アマ,アマ,アマ,空白,ヒキ,ヒキ,ヒキ, LV 2=アマ,アマ,アマ,ヒキ,空白,ヒキ,ヒキ, LV 3=アマ,アマ,空白,ヒキ,アマ,ヒキ,ヒキ, LV 4=アマ,空白,アマ,ヒキ,アマ,ヒキ,ヒキ, LV 5=アマ,ヒキ,アマ,空白,アマ,ヒキ,ヒキ, LV 6=アマ,ヒキ,アマ,ヒキ,アマ,空白,ヒキ, LV 7=アマ,ヒキ,アマ,ヒキ,アマ,ヒキ,空白, LV 8=アマ,ヒキ,アマ,ヒキ,空白,ヒキ,アマ, LV 9=アマ,ヒキ,空白,ヒキ,アマ,ヒキ,アマ, LV10=空白,ヒキ,アマ,ヒキ,アマ,ヒキ,アマ, LV11=ヒキ,空白,アマ,ヒキ,アマ,ヒキ,アマ, LV12=ヒキ,ヒキ,アマ,空白,アマ,ヒキ,アマ, LV13=ヒキ,ヒキ,アマ,ヒキ,アマ,空白,アマ, LV14=ヒキ,ヒキ,アマ,ヒキ,空白,アマ,アマ, LV15=ヒキ,ヒキ,空白,ヒキ,アマ,アマ,アマ, LV16=ヒキ,ヒキ,ヒキ,空白,アマ,アマ,アマ, 解2を発見しました。 LV 1=アマ,アマ,アマ,空白,ヒキ,ヒキ,ヒキ, LV 2=アマ,アマ,空白,アマ,ヒキ,ヒキ,ヒキ, LV 3=アマ,アマ,ヒキ,アマ,空白,ヒキ,ヒキ, LV 4=アマ,アマ,ヒキ,アマ,ヒキ,空白,ヒキ, LV 5=アマ,アマ,ヒキ,空白,ヒキ,アマ,ヒキ, LV 6=アマ,空白,ヒキ,アマ,ヒキ,アマ,ヒキ, LV 7=空白,アマ,ヒキ,アマ,ヒキ,アマ,ヒキ, LV 8=ヒキ,アマ,空白,アマ,ヒキ,アマ,ヒキ, LV 9=ヒキ,アマ,ヒキ,アマ,空白,アマ,ヒキ, LV10=ヒキ,アマ,ヒキ,アマ,ヒキ,アマ,空白, LV11=ヒキ,アマ,ヒキ,アマ,ヒキ,空白,アマ, LV12=ヒキ,アマ,ヒキ,空白,ヒキ,アマ,アマ, LV13=ヒキ,空白,ヒキ,アマ,ヒキ,アマ,アマ, LV14=ヒキ,ヒキ,空白,アマ,ヒキ,アマ,アマ, LV15=ヒキ,ヒキ,ヒキ,アマ,空白,アマ,アマ, LV16=ヒキ,ヒキ,ヒキ,空白,アマ,アマ,アマ,
レベルの上限の初期値を(6+5+4)*2の30として、 深さ優先探索で探索してます。