我如何在不使用LINQ的情况下找到列表中缺失的数字
本文关键字:列表 数字 情况下 LINQ | 更新日期: 2023-09-27 18:07:40
public static class MyExtensions
{
/// <summary>
/// Finds the missing numbers in a list.
/// </summary>
/// <param name="list">List of numbers</param>
/// <returns>Missing numbers</returns>
public static IEnumerable<int> FindMissing(this List<int> list)
{
// Sorting the list
list.Sort();
// First number of the list
var firstNumber = list.First();
// Last number of the list
var lastNumber = list.Last();
// Range that contains all numbers in the interval
// [ firstNumber, lastNumber ]
var range = Enumerable.Range(firstNumber, lastNumber - firstNumber);
// Getting the set difference
var missingNumbers = range.Except(list);
return missingNumbers;
}
}
现在您可以通过以下方式调用扩展方法:
class Program
{
static void Main(string[] args)
{
// List of numbers
List<int> daysOfMonth =
new List<int>() { 6, 2, 4, 1, 9, 7, 3, 10, 15, 19, 11, 18, 13, 22, 24, 20, 27, 31, 25, 28 };
Console.Write("'nList of days: ");
foreach(var num in daysOfMonth)
{
Console.Write("{0} ", num);
}
Console.Write("'n'nMissing days are: ");
// Calling the Extension Method in the List of type int
foreach(var number in daysOfMonth.FindMissing())
{
Console.Write("{0} ", number);
}
}
}
public static IEnumerable<int> FindMissing(List<int> list)
{
if (list.Count < 3) yield break;
List<int> listClone = new List<int>(list); //do not modify the original list
listClone.Sort();
for (int n = listClone[i] ; n < listClone[listClone.Count - 1]; n++)
if (!listClone.Contains(n))
yield return n;
}
当然,这可以优化为不遍历整个listClone
实际上,您自己的代码并没有完成预期的工作。
方法文档假设FindMissing
将发现Min
中缺少的数字。列表的Max
范围。相反,该方法实际上查找列表中第一个值和最后一个值之间缺失的数字。换句话说,在给定的示例中,我期望从1到31进行搜索。相反,该方法将搜索从6到28。
现在,如果您需要将其转换为非linq方法,请逐步尝试:
-
该方法使用
list.First()
和list.Last()
。您可以使用索引和list.Count
来获得这两个值。 -
该方法使用
Enumerable.Range
。该行为很容易通过for
循环重现。 -
方法使用
IEnumerable.Except()
。您可以通过遍历列表来查找缺失的值。