如何从开始直到特定条件中删除通用列表中的项
本文关键字:删除 列表 特定条件 开始 | 更新日期: 2023-09-27 18:06:16
我有一个像下面这样的通用列表,
var steps = new List<Step>
{
new Step { From = "A", To = "D", Quantity = 0 },
new Step { From = "D", To = "J", Quantity = 0 },
new Step { From = "J", To = "T", Quantity = 0 },
new Step { From = "D", To = "K", Quantity = 0 },
new Step { From = "K", To = "T", Quantity = 0 },
new Step { From = "E", To = "K", Quantity = 0 },
new Step { From = "A", To = "E", Quantity = 0 },
new Step { From = "B", To = "E", Quantity = 0 },
new Step { From = "E", To = "L", Quantity = 5 },
new Step { From = "B", To = "F", Quantity = 5 },
new Step { From = "B", To = "G", Quantity = 5 },
new Step { From = "F", To = "I", Quantity = 5 },
new Step { From = "G", To = "I", Quantity = 5 },
new Step { From = "C", To = "H", Quantity = 0 },
new Step { From = "H", To = "Z", Quantity = 0 },
new Step { From = "H", To = "Y", Quantity = 0 },
new Step { From = "H", To = "X", Quantity = 5 },
new Step { From = "X", To = "I", Quantity = 5 },
new Step { From = "I", To = "V", Quantity = 5 },
new Step { From = "L", To = "V", Quantity = 5 },
new Step { From = "Y", To = "V", Quantity = 5 },
new Step { From = "Y", To = "M", Quantity = 0 },
new Step { From = "Z", To = "M", Quantity = 0 },
new Step { From = "Z", To = "N", Quantity = 0 },
new Step { From = "M", To = "O", Quantity = 0 },
};
我想从列表中删除项目。它将开始列表的第一个项目。它将删除项目,直到下一个项目的数量大于零。它应该反过来做同样的工作。
就像string.Trim('0')
。
结果应该如下所示:
var steps = new List<Step>
{
new Step { From = "E", To = "L", Quantity = 5 },
new Step { From = "B", To = "F", Quantity = 5 },
new Step { From = "B", To = "G", Quantity = 5 },
new Step { From = "F", To = "I", Quantity = 5 },
new Step { From = "G", To = "I", Quantity = 5 },
new Step { From = "C", To = "H", Quantity = 0 },
new Step { From = "H", To = "Z", Quantity = 0 },
new Step { From = "H", To = "Y", Quantity = 0 },
new Step { From = "H", To = "X", Quantity = 5 },
new Step { From = "X", To = "I", Quantity = 5 },
new Step { From = "I", To = "V", Quantity = 5 },
new Step { From = "L", To = "V", Quantity = 5 },
new Step { From = "Y", To = "V", Quantity = 5 },
};
您想要这样的内容:
steps = steps.SkipWhile(s => s.Quantity == 0).Reverse()
.SkipWhile(s => s.Quantity == 0).Reverse()
.ToList();
我想这将是"简单"的解决方案。首先查找steps
的期望范围的边界,然后再使用GetRange
得到该范围的边界,这样会更快。
我认为,最好的选择是重新分配step
到新的列表
list = list.SkipWhile(s => s.Quantity == 0).ToList();
UPD:是的,我的错,我只做了TrimStart
。注意力不集中。
这应该能奏效:
steps = steps
.SkipWhile(step => step.Quantity == 0)
.TakeWhile((step, index) =>
steps.Skip(index).Any(nextSteps => nextSteps.Quantity != 0))
.ToList();
SkipWhile
首先跳过所有quantity=0的步骤,然后执行所有以下步骤中quantity=0的步骤
虽然简单的解决方案是重复两次列表,但对于大列表来说可能会变得昂贵。
list = list.SkipWhile(s => s.Quantity == 0).Reverse()
.SkipWhile( s => s.Quantity == 0).Reverse().ToList();
一个更有效的解决方案是这样定义一个扩展方法:
public static IEnumerable TrimLast(IEnumerable<T> this, Func<T, Bool> cond) {
foreach (var item in this) {
if (!cond(item)) {
foreach (var storeditem in store) {
yield return storeditem;
}
store.Clear;
yield return item;
} else {
store.Add(item);
}
}
}
则称其为:list = list.SkipWhile(s => s.Quantity == 0).TrimLast(s => s.Quantity == 0).ToList();
这样做的优点是永远不会存储超过最长的连续零序列,而不像反向解决方案需要存储整个列表两次。