24点计算
最编程
2024-02-04 11:54:01
...
public static class Permutation
{
public static void ForEach<T>(this IEnumerable<T> enumerable, Action<T> action)
{
foreach(T t in enumerable)
{
action(t);
}
}
/// <summary>
/// delete an object from an object array (use reference equal to compare two objects)
/// </summary>
/// <param name="objs"></param>
/// <param name="v"></param>
/// <returns></returns>
private static Object[] SkipByReference(Object[] objs, Object v)
{
return objs.Where(x => !Object.ReferenceEquals(x, v)).ToArray();
}
/// <summary>
/// generate all permutations of objects in objs
/// </summary>
/// <param name="objs"></param>
/// <returns></returns>
public static IEnumerable<Object[]> GetPernumtation(Object[] objs)
{
Int32 n = objs.Length;
Debug.Assert(n > 0);
if (n == 1)
{
yield return objs;
}
else
{
Object[] current = new Object[n];
for (int i = 0; i < n; ++i)
{
current[0] = objs[i];
foreach (Object[] next in GetPernumtation(SkipByReference(objs, objs[i])))
{
Array.Copy(next, 0, current, 1, n - 1);
yield return current.Clone() as Object[];
}
}
}
}
/// <summary>
/// Generate repeatable
/// </summary>
/// <param name="objs"></param>
/// <param name="resultCount"></param>
/// <returns></returns>
public static IEnumerable<Object[]> GetRepeatablePermutation(Object[] objs, int resultCount)
{
if (resultCount == 1)
{
foreach (Object obj in objs)
{
yield return new Object[] { obj };
}
}
else
{
Object[] result = new Object[resultCount];
for (int i = 0; i < objs.Length; ++i)
{
result[0] = objs[i];
foreach (Object[] next in GetRepeatablePermutation(objs, resultCount - 1))
{
Array.Copy(next, 0, result, 1, resultCount - 1);
yield return result.Clone() as Object[];
}
}
}
}
/// <summary>
/// Generate all sequences of possible push ans pop in form of String like "XXXYYY"
/// X means push and Y means pop
/// </summary>
/// <param name="n"></param>
/// <returns></returns>
public static IEnumerable<String> GenerateStackOperateSequences(int n)
{
Char[] results = new Char[2 * n];
return GenerateStackOperateSequencesPrivate(results, 0, n, n).Select(x=>new String(x));
}
private static IEnumerable<Char[]> GenerateStackOperateSequencesPrivate(char[] results, int moreX, int leftX, int leftY)
{
int startIndex = results.Length - leftX - leftY;
if (startIndex == results.Length)
{
yield return results.Clone() as char[];
}
if (moreX > 0)
{
results[startIndex] = 'Y';
foreach(var v in GenerateStackOperateSequencesPrivate(results, moreX - 1, leftX, leftY - 1))
{
yield return v;
}
}
if (leftX > 0)
{
results[startIndex] = 'X';
foreach (var v in GenerateStackOperateSequencesPrivate(results, moreX + 1, leftX - 1, leftY))
{
yield return v;
}
}
yield break;
}
}
private static IEnumerable<Instruction[]> GenerateInsructions(Object[] operands,
Instruction[] instructionCandidates)
{
string[] patterns = Permutation.GenerateStackOperateSequences(operands.Length - 1).Select(x => 'X' + x).ToArray();
int instructionCountExpected = operands.Count() - 1;
List<Object[]> operantsCandidate = new List<object[]>(
Permutation.GetPernumtation(operands));
List<Object[]> instructionCandiatesList = new List<Object[]>(
Permutation.GetRepeatablePermutation(instructionCandidates, instructionCountExpected));
List<Instruction> result = new List<Instruction>();
foreach (Object[] operants in operantsCandidate)
{
Queue<Object> operantsQueue = new Queue<object>(operants);
foreach (Object[] instructions in instructionCandiatesList)
{
foreach (String pattern in patterns)
{
int iA = 0;
int iB = 0;
result.Clear();
for (int i = 0; i < pattern.Length; ++i)
{
if (pattern[i] == 'X')
{
result.Add(new LoadInstruction(operants[iA++]));
}
else
{
result.Add(instructions[iB++] as Instruction);
}
}
yield return result.ToArray();
}
}
}
}
{
public static void ForEach<T>(this IEnumerable<T> enumerable, Action<T> action)
{
foreach(T t in enumerable)
{
action(t);
}
}
/// <summary>
/// delete an object from an object array (use reference equal to compare two objects)
/// </summary>
/// <param name="objs"></param>
/// <param name="v"></param>
/// <returns></returns>
private static Object[] SkipByReference(Object[] objs, Object v)
{
return objs.Where(x => !Object.ReferenceEquals(x, v)).ToArray();
}
/// <summary>
/// generate all permutations of objects in objs
/// </summary>
/// <param name="objs"></param>
/// <returns></returns>
public static IEnumerable<Object[]> GetPernumtation(Object[] objs)
{
Int32 n = objs.Length;
Debug.Assert(n > 0);
if (n == 1)
{
yield return objs;
}
else
{
Object[] current = new Object[n];
for (int i = 0; i < n; ++i)
{
current[0] = objs[i];
foreach (Object[] next in GetPernumtation(SkipByReference(objs, objs[i])))
{
Array.Copy(next, 0, current, 1, n - 1);
yield return current.Clone() as Object[];
}
}
}
}
/// <summary>
/// Generate repeatable
/// </summary>
/// <param name="objs"></param>
/// <param name="resultCount"></param>
/// <returns></returns>
public static IEnumerable<Object[]> GetRepeatablePermutation(Object[] objs, int resultCount)
{
if (resultCount == 1)
{
foreach (Object obj in objs)
{
yield return new Object[] { obj };
}
}
else
{
Object[] result = new Object[resultCount];
for (int i = 0; i < objs.Length; ++i)
{
result[0] = objs[i];
foreach (Object[] next in GetRepeatablePermutation(objs, resultCount - 1))
{
Array.Copy(next, 0, result, 1, resultCount - 1);
yield return result.Clone() as Object[];
}
}
}
}
/// <summary>
/// Generate all sequences of possible push ans pop in form of String like "XXXYYY"
/// X means push and Y means pop
/// </summary>
/// <param name="n"></param>
/// <returns></returns>
public static IEnumerable<String> GenerateStackOperateSequences(int n)
{
Char[] results = new Char[2 * n];
return GenerateStackOperateSequencesPrivate(results, 0, n, n).Select(x=>new String(x));
}
private static IEnumerable<Char[]> GenerateStackOperateSequencesPrivate(char[] results, int moreX, int leftX, int leftY)
{
int startIndex = results.Length - leftX - leftY;
if (startIndex == results.Length)
{
yield return results.Clone() as char[];
}
if (moreX > 0)
{
results[startIndex] = 'Y';
foreach(var v in GenerateStackOperateSequencesPrivate(results, moreX - 1, leftX, leftY - 1))
{
yield return v;
}
}
if (leftX > 0)
{
results[startIndex] = 'X';
foreach (var v in GenerateStackOperateSequencesPrivate(results, moreX + 1, leftX - 1, leftY))
{
yield return v;
}
}
yield break;
}
}
private static IEnumerable<Instruction[]> GenerateInsructions(Object[] operands,
Instruction[] instructionCandidates)
{
string[] patterns = Permutation.GenerateStackOperateSequences(operands.Length - 1).Select(x => 'X' + x).ToArray();
int instructionCountExpected = operands.Count() - 1;
List<Object[]> operantsCandidate = new List<object[]>(
Permutation.GetPernumtation(operands));
List<Object[]> instructionCandiatesList = new List<Object[]>(
Permutation.GetRepeatablePermutation(instructionCandidates, instructionCountExpected));
List<Instruction> result = new List<Instruction>();
foreach (Object[] operants in operantsCandidate)
{
Queue<Object> operantsQueue = new Queue<object>(operants);
foreach (Object[] instructions in instructionCandiatesList)
{
foreach (String pattern in patterns)
{
int iA = 0;
int iB = 0;
result.Clear();
for (int i = 0; i < pattern.Length; ++i)
{
if (pattern[i] == 'X')
{
result.Add(new LoadInstruction(operants[iA++]));
}
else
{
result.Add(instructions[iB++] as Instruction);
}
}
yield return result.ToArray();
}
}
}
}
上一篇: 简单易懂! DFS算法如何计算24点?
下一篇: 算24点
推荐阅读
-
学习 Excel 函数的到期日计算,EDATE 函数的几个应用示例
-
示例详细说明了如何用 php 实现圆的面积计算
-
python 固定资产管理系统 python 计算固定资产折旧
-
Python 计算期初余额与本期收回或转回金额之间的差额 期初余额 期初余额 计算公式
-
计算机 2 c 语言(考试更正题汇总 II)
-
2019-02-24 计算机二级 C 级课后习题 (1)
-
国王大道计算机网络 BGP 协议
-
ARP 协议有什么作用--ARP(AddressResolutionProtocol,地址解析协议)地址解析协议用于将计算机的网络地址(32 位 IP 地址)转换为物理地址(48 位 MAC 地址)[RFC826]。ARP 协议属于链路层协议,在以太网网络中,数据帧从一台主机传送到网络中的另一台主机时,是根据 48 位以太网地址(硬件地址)来确定接口的,而不是根据 32 位 IP 地址。内核(如驱动程序)必须知道目的地的硬件地址,才能发送数据。当然,点对点连接不需要 ARP 协议。 ARP 协议示例
-
[容器和云计算的网络类型
-
A" 标记:我的云计算 HCIE 之旅