我试图找出使用存储在List中的两个其他数字之间的任何n在整数列表中找到最接近的值ROUNDED DOWN的最佳方法。在这种情况下,所有整数都将是无符号的,以防万一。
假设如下:
Math.Abs
)例如:
List<int> numbers = new List<int>() { 0, 2000, 4000, 8000, 8500, 9101, 10010 };
int myNumber = 9000;
int theAnswer; // should be 8500
for (int i = 0; i < numbers.Count; i++) {
if (i == numbers.Count - 1) {
theAnswer = numbers[i];
break;
} else if (myNumber < numbers[i + 1]) {
theAnswer = numbers[i];
break;
}
}
上一个代码示例没有任何缺陷。
是否有更好更多的方式来做这件事?
答案 0 :(得分:5)
您可以使用List<T>.BinarySearch代替按顺序枚举列表元素。
List<int> numbers = new List<int>() { 0, 2000, 4000, 8000, 8500, 9101, 10010 };
int myNumber = 9000;
int r=numbers.BinarySearch(myNumber);
int theAnswer=numbers[r>=0?r:~r-1];
答案 1 :(得分:4)
过滤列表获取小于myNumber
的所有值并返回最后一个:
theAnswer = numbers.Where(x => x <= myNumber ).Last();
答案 2 :(得分:0)
列表可以编入索引。
从列表中间的索引处开始。如果你找到了确切的数字,那你很好。如果该数字小于目标数字,则在从列表开头到小于列表中间的范围的中间搜索。如果该数字大于目标数字,则使用列表的另一半。继续此二进制搜索,直到找到完全匹配,或者相邻的数字小于和大于目标数字。
选择两者中较小的一个。
答案 3 :(得分:0)
请尝试以下代码:
List<int> numbers = new List<int>() { 0, 2000, 4000, 8000, 8500, 9101, 10010 };
int myNumber = 9000;
int theAnswer = numbers[numbers.Count - 1];
if (theAnswer > myNumber)
{
int l = 0, h = numbers.Count - 1, m;
do
{
m = (int)((double)(myNumber - numbers[l]) / (double)(numbers[h] - numbers[l]) * (h - l) + l);
if (numbers[m] > myNumber) h = m; else l = m;
}
while ((h - l) != 1);
theAnswer = numbers[l];
}