你的解决方案有什么问题?
虽然您在代码中正确地保留了名为n 的表中数字的频率,因此我将其称为frequencies,然后您将Sort 这个数组。此操作会破坏您的解决方案,因为每个频率都与其在数组中的位置的相应索引相关联。
例如如果这个数组的一个实例是这个[8,2,1,7,6]。当你在这个数组上调用Sort 方法时,这将导致数组被排序并且数组元素的顺序将是[1,2,7,6,8]。在调用 sort 之前,数组的第一个元素表示在我们的numbers 中已经找到了 8 次数字 0(第一个元素的索引为 0)。排序后,第一个元素是1,这意味着现在数字0出现的频率是1,这显然是错误的。
如果你想保持自己的方式,那么你可以尝试这样的事情:
int[] numbers = { 1,2,2,9,1,2,5,5,5,5,2 };
int[] frequencies = new int[12];
int k = 3;
foreach (int number in numbers)
{
frequencies[number]++;
}
var mostFrequentNumbers = frequencies.Select((frequency, index) => new
{
Number = index,
Frequency = frequency
})
.OrderByDescending(item => item.Frequency)
.Select(item => item.Number)
.Take(k);
foreach (int mostFrequentNumber in mostFrequentNumbers)
{
Console.WriteLine(mostFrequentNumber);
}
还有其他方法吗?
一个简单的方法是使用像字典这样的数据结构,您可以在其中将数字作为键,将相应的频率作为相应的值。
然后您可以按上述数据结构的降序排列,并保留 k 个最频繁的数字。
int[] numbers = { 1,2,2,9,1,2,5,5,5,5,2 };
int k = 3;
Dictionary<int, int> numberFrequencies = new Dictionary<int, int>();
foreach (int number in numbers)
{
if(numberFrequencies.ContainsKey(number))
{
numberFrequencies[number] += 1;
}
else
{
numberFrequencies.Add(number, 1);
}
}
var mostFrequentNumbers = numberFrequencies.OrderByDescending(numberFrequency => numberFrequency.Value)
.Take(k)
.Select(numberFrequency => numberFrequency.Key);
foreach (int mostFrequentNumber in mostFrequentNumbers)
{
Console.WriteLine(mostFrequentNumber);
}
您也可以仅使用 LINQ 实现相同的目标:
int[] numbers = { 1,2,2,9,1,2,5,5,5,5,2 };
int k = 3;
var mostFrequentNumbers = numbers.GroupBy(number => number)
.ToDictionary(gr => gr.Key, gr => gr.Count())
.OrderByDescending(keyValue => keyValue.Value)
.Take(k)
.Select(numberFrequency => numberFrequency.Key);
foreach (int mostFrequentNumber in mostFrequentNumbers)
{
Console.WriteLine(mostFrequentNumber);
}