繁体   English   中英

最佳实践 - 从C#中的泛型集合中删除项目

[英]Best Practice - Removing item from generic collection in C#

我在Visual Studio 2008中使用C#和.NET 3.5。

我有一个通用字典,它将事件类型映射到通用的订阅者列表。 订阅者可以订阅多个事件。

private static Dictionary<EventType, List<ISubscriber>> _subscriptions;

要从订阅列表中删除订阅者,我可以使用这两个选项中的任何一个。

选项1:

ISubscriber subscriber;  // defined elsewhere
foreach (EventType event in _subscriptions.Keys) {
    if (_subscriptions[event].Contains(subscriber)) {
        _subscriptions[event].Remove(subscriber);
    }
}

选项2:

ISubscriber subscriber;  // defined elsewhere
foreach (EventType event in _subscriptions.Keys) {
    _subscriptions[event].Remove(subscriber);
}

我有两个问题。

首先,请注意选项1在删除项目之前检查是否存在,而选项2使用强力删除,因为Remove()不会抛出异常。 在这两个中,这是首选的“最佳实践”方式吗?

第二,是否有另一种“更干净”,更优雅的方式来实现这一点,可能使用lambda表达式或使用LINQ扩展? 我仍然适应这两个功能。

谢谢。

编辑

为了澄清,我意识到选项1和2之间的选择是速度(选项2)与可维护性(选项1)的选择。 在这种特殊情况下,我不一定会尝试优化代码,尽管这肯定是值得考虑的。 我想要了解的是,如果这样做有一个普遍成熟的做法。 如果没有,您将在自己的代码中使用哪个选项?

选项1将比选项2慢.Lambda表达式和LINQ将更慢。 我会使用HashSet<>而不是List<>

如果您需要有关项目删除的确认,则必须使用Contains

编辑:由于在lock语句中使用代码的概率很高,并且最佳做法是减少lock内部的执行时间,因此应用选项2可能很有用。看起来没有最佳实践可以使用或不使用 -使用Contains Remove

Remove()方法'approches O(1)'并且当一个键不存在时是OK。

但除此之外:如果有疑问,请测量。 获得一些时间并不困难......

当你所关心的只是值时,为什么要枚举键?

foreach (List<ISubscriber> list in _subscriptions.Values)
{
    list.Remove(subscriber);
}

也就是说,Eric P建议的LINQ解决方案肯定更简洁。 但是,性能可能是一个问题。

我会选择第二种选择。 Contains()和Remove()都是O(n)方法,没有理由同时调用它们,因为Remove不会抛出。 至少在方法2中,您只需要调用一个昂贵的操作而不是两个操作。

我不知道有更快的方法来处理它。

如果你想使用Linq来做这件事,我认为这样可行(未经测试):

_subscriptions.Values.All(x => x.Remove(subscriber));

可能想要检查性能。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM