如何使用 C# 代码重写这个使用扩展运算符的 javascript 函数?
How to rewrite this javascript function that uses spread operator using C# code?
我正在尝试使用 C# 代码重写此 的答案。由于 C# 没有普及,而且我们遇到越界异常,这是一项艰巨的任务。我设法编写了以下代码,它的工作原理,但我相信有更好的方法来做到这一点。
int? result = MaxCollectableTreasure(new List<int?>() {1, 3, 1, 8, 7 }, 3);
int? MaxCollectableTreasure(List<int?> chests, int minutes)
{
if (chests.Count == 1 && minutes > 0)
return chests[0];
int? firstElement = chests[0];
var restOfList = chests.Skip(1).Take(chests.Count).ToList();
return MaxCollectableTreasuresRecursive(firstElement, restOfList, minutes);
}
int? MaxCollectableTreasuresRecursive(int? firstElement, List<int?> chests, int minutes)
{
if (minutes == 0 || firstElement is null)
return 0;
if (firstElement == 0)
return MaxCollectableTreasuresRecursive(chests.FirstOrDefault(), AllButFirst(chests), minutes - 1);
var left = firstElement + MaxCollectableTreasuresRecursive(0, AllButFirst(chests.Prepend(0)), minutes - 1);
var right = MaxCollectableTreasuresRecursive(chests.FirstOrDefault(), AllButFirst(chests), minutes - 1);
int leftAsInt = left ?? 0;
int rightAsInt = right ?? 0;
return Math.Max(leftAsInt, rightAsInt);
}
List<int?> AllButFirst(IEnumerable<int?> chests)
{
return chests.Skip(1).Take(chests.Count()).ToList();
}
你在这里有一个非常漂亮的实现,它很快就解决了这个问题。
我只能看到你在这里的性能有微小的改进,这会增加执行时间。
int? result = MaxCollectableTreasure(new List<int?>() { 1, 3, 1, 8, 7 }, 3);
int? MaxCollectableTreasure(IReadOnlyList<int?> chests, int minutes)
{
if (chests.Count == 1 && minutes > 0)
return chests[0];
int? firstElement = chests[0];
var restOfList = chests.Skip(1);
return MaxCollectableTreasuresRecursive(firstElement, restOfList, minutes);
}
int? MaxCollectableTreasuresRecursive(int? firstElement, IEnumerable<int?> chests, int minutes)
{
while (true)
{
if (minutes == 0 || firstElement is null) return 0;
if (firstElement == 0)
{
firstElement = chests.FirstOrDefault();
chests = chests.Skip(1);
minutes -= 1;
continue;
}
var left = firstElement + MaxCollectableTreasuresRecursive(0, chests, minutes - 1);
var right = MaxCollectableTreasuresRecursive(chests.FirstOrDefault(), chests.Skip(1), minutes - 1);
int leftAsInt = left ?? 0;
int rightAsInt = right ?? 0;
return Math.Max(leftAsInt, rightAsInt);
}
}
首先是您不需要 .Take().ToList()
来取回箱子,只需 .Skip()
自己就可以完成您需要的事情。
同样在计算左边的值时,您将 0 添加到胸部,然后在其上跳过 1,以便可以将其删除以整理该位。
不过必须说,您对 Javascript 等价物的解释非常巧妙!
我正在尝试使用 C# 代码重写此
int? result = MaxCollectableTreasure(new List<int?>() {1, 3, 1, 8, 7 }, 3);
int? MaxCollectableTreasure(List<int?> chests, int minutes)
{
if (chests.Count == 1 && minutes > 0)
return chests[0];
int? firstElement = chests[0];
var restOfList = chests.Skip(1).Take(chests.Count).ToList();
return MaxCollectableTreasuresRecursive(firstElement, restOfList, minutes);
}
int? MaxCollectableTreasuresRecursive(int? firstElement, List<int?> chests, int minutes)
{
if (minutes == 0 || firstElement is null)
return 0;
if (firstElement == 0)
return MaxCollectableTreasuresRecursive(chests.FirstOrDefault(), AllButFirst(chests), minutes - 1);
var left = firstElement + MaxCollectableTreasuresRecursive(0, AllButFirst(chests.Prepend(0)), minutes - 1);
var right = MaxCollectableTreasuresRecursive(chests.FirstOrDefault(), AllButFirst(chests), minutes - 1);
int leftAsInt = left ?? 0;
int rightAsInt = right ?? 0;
return Math.Max(leftAsInt, rightAsInt);
}
List<int?> AllButFirst(IEnumerable<int?> chests)
{
return chests.Skip(1).Take(chests.Count()).ToList();
}
你在这里有一个非常漂亮的实现,它很快就解决了这个问题。
我只能看到你在这里的性能有微小的改进,这会增加执行时间。
int? result = MaxCollectableTreasure(new List<int?>() { 1, 3, 1, 8, 7 }, 3);
int? MaxCollectableTreasure(IReadOnlyList<int?> chests, int minutes)
{
if (chests.Count == 1 && minutes > 0)
return chests[0];
int? firstElement = chests[0];
var restOfList = chests.Skip(1);
return MaxCollectableTreasuresRecursive(firstElement, restOfList, minutes);
}
int? MaxCollectableTreasuresRecursive(int? firstElement, IEnumerable<int?> chests, int minutes)
{
while (true)
{
if (minutes == 0 || firstElement is null) return 0;
if (firstElement == 0)
{
firstElement = chests.FirstOrDefault();
chests = chests.Skip(1);
minutes -= 1;
continue;
}
var left = firstElement + MaxCollectableTreasuresRecursive(0, chests, minutes - 1);
var right = MaxCollectableTreasuresRecursive(chests.FirstOrDefault(), chests.Skip(1), minutes - 1);
int leftAsInt = left ?? 0;
int rightAsInt = right ?? 0;
return Math.Max(leftAsInt, rightAsInt);
}
}
首先是您不需要 .Take().ToList()
来取回箱子,只需 .Skip()
自己就可以完成您需要的事情。
同样在计算左边的值时,您将 0 添加到胸部,然后在其上跳过 1,以便可以将其删除以整理该位。
不过必须说,您对 Javascript 等价物的解释非常巧妙!