如何查找列表是否包含Interval中的键

时间:2013-12-14 22:37:00

标签: c# intervals sortedlist

我有一个<key,value>元素的排序列表。 关键是unsigned int。

在C#中是否有任何快速有效的方法来确定在给定间隔的情况下,列表是否包含在该间隔中具有键的元素?

4 个答案:

答案 0 :(得分:1)

起初我错过了您的清单已分类的要点
似乎可能,是的,在O(log N)中
假设您的间隔是[A,B] 假设你的号码中有数字C1,C2,... CN 对于每个K,列表和C [K]&lt; = C [K + 1]
1)求出最小K1,使得C [K1]> = A
如果找不到K1,则回答“未找到”
2)求出最大K2,使得C [K2] <= B
如果找不到K2,则回答“未找到”
3)最后,如果K1&lt; = K2回答是“找到”,则 否则答案是“未找到”。

对于1)和2)你可以使用二进制搜索。
所以你需要做的就是用C#编写代码。

答案 1 :(得分:0)

如果您的列表包含完整的正数,那么您可以使用LINQ AnyEnumerable.Range to create the range to checkList.Contains轻松构建自己的函数。代码可能如下所示:

var list = new List<int> { 1, 2, 3, 4, 5, 10, 100, 1000 };
// range to check
var min = 15;
var max = 18;
Console.WriteLine(list.Any (l => Enumerable.Range(min, max - min).ToList().Contains(l)) ? "Yes" : "No");

输出适用于 [15-18] [9-11] 。< / p>

另一种可能性(比第一种更快)是@ peter.petrov建议直接在给定间隔内搜索(使用列表上的LINQ where clause):

var list = new List<int> { 1, 2, 3, 4, 5, 10, 100, 1000 };
// range to check
var min = 15;
var max = 18;
Console.WriteLine(list.Where (l => l > min && l < max).ToList().Count() > 0 ? "Yes" : "No");

输出与第一个代码示例中的相同。

此方法可以应用于任何实现IEnumerable接口的类。使用SortedList的一个解决方案可能如下所示:

var list = new SortedList<int, int> { {1, 1}, {2, 2}, {3, 3}, {4, 10}, {5, 100} };
// range to check
var min = 15;
var max = 18;
Console.WriteLine(list.Where (l => l.Value > min && l.Value < max).ToList().Count () > 0 ? "Yes" : "No");

答案 2 :(得分:0)

SortedList有一个名为ContainKey()的方法,它确定SortedList对象是否包含特定密钥,并且由于带下划线的实现使用二叉搜索树,因此使用o(log N)在内部确定。但是在你的情况下它是一系列键。所以我建议你在你的范围内写一个二进制搜索。

答案 3 :(得分:0)

这将是最快的解决方案,因为SortedList.ContainsKey实现了Dictionary.ContainsKey并且它已经是O(log n)操作。如果您只是寻找会员资格,也可以在第一场比赛中保释。

SortedList<uint, int> n = new SortedList<uint, int>();

private bool KeyInRange(uint rangemin, uint rangemax;){
    for (uint i=rangemin; i<=rangemax; i++)
        if(n.ContainsKey(i))
            return true;

    return false;
}