0

我将如何根据以下条件删除字典中的指定键?

foreach (var kvp in dict)
            {
                if (kvp.Key.Contains('/'))
                {
                    //delete the key
                }
            }
4

6 回答 6

9

你会这样做:

foreach(var keyToDelete in dict.Keys.Where(x => x.Contains('/')).ToList())
    dict.Remove(keyToDelete);

这里重要的是ToList()调用Where. 这会将所有应该删除的键放入一个可以迭代的新列表中。
如果您在没有的情况下尝试此代码,ToList()您将获得InvalidOperationException

收藏已修改;枚举操作可能无法执行。

请注意,此代码比当前接受的答案更有效。它只复制需要删除的键而不是完整的字典。

于 2013-02-13T07:54:08.400 回答
3

问题是您不能在循环遍历集合元素时修改集合。解决方案是将要删除的键放在不同的集合中,然后循环遍历以删除元素。这就是丹尼尔的回答。

如果你不能/不想使用 LINQ,你可以这样做:

List<YourKeyType> toRemove = new List<YourKeyType>();
foreach (var kvp in dict)
{
    if (kvp.Key.Contains('/'))
        toRemove.Add(kvp.Key);
}
foreach (var aKey in toRemove)
    dict.Remove(aKey);
于 2013-02-13T08:27:16.060 回答
2

根据您的数据集,在没有要丢弃的键的情况下创建新对象可能更有效:

dict = dict.Where(kvp => !kvp.Key.Contains('/'))
           .ToDictionary(kvp => kvp.Key, kvp => kvp.Value);

我还可以争辩说,这比删除键更可取,因为它更清楚地传达了代码的意图,但这与我的个人编码风格密切相关,因此您的里程可能会有所不同。

于 2013-02-13T08:20:20.047 回答
2

我意识到这已经被标记为已回答,但我认为如果您只想从未指定最大大小的字典中删除一个键,则复制整个字典只是为了删除一个键不是一个好的解决方案!

要删除匹配键的一个条目,您可以这样做:

foreach (var kvp in dict)
{
    if (kvp.Key.Contains('/'))
    {
        dict.Remove(kvp.Key);
        break;
    }
}

不需要整个字典的副本!

请注意,这假设只有一个密钥要删除。如果可能还有更多,请使用上面 Daniel 或 Francesco 的答案。

(实际上,我建议您只使用 Daniel 的答案,但我将在此处留下这个作为示例,而不使用 Linq。)

于 2013-02-13T08:37:50.067 回答
1

编辑:正如下面其他答案所说,下面代码中重要的是调用 ToList()。这将创建一个 dict 副本,您可以在从 dict 中删除项目时对其进行迭代,而无需更改您正在迭代的集合。

你可以通过使用类似的东西来做到这一点

    dict.ToList().ForEach(a => { if (a.Key.Contains('/') dict.Remove(a.Key); });
于 2013-02-13T07:58:45.900 回答
-2

Foreach 可能会抛出异常。尝试使用 for 代替。

对于删除,请使用 Remove 方法。

于 2013-02-13T07:54:34.237 回答