The*_*ias 5 c# dictionary .net-core
我正在尝试实现一种用于安全地枚举集合的缓存机制,并且正在检查内置集合的所有修改是否触发了InvalidOperationException由其各自的枚举器抛出的异常。我注意到,在.NET Core平台中,Dictionary.Remove和Dictionary.Clear方法没有触发此异常。这是错误还是功能?
范例Remove:
var dictionary = new Dictionary<int, string>();
dictionary.Add(1, "Hello");
dictionary.Add(2, "World");
foreach (var entry in dictionary)
{
var removed = dictionary.Remove(entry.Key);
Console.WriteLine($"{entry} removed: {removed}");
}
Console.WriteLine($"Count: {dictionary.Count}");
Run Code Online (Sandbox Code Playgroud)
输出:
[1,Hello]已删除:True
[2,World]已删除:True
计数:0
范例Clear:
var dictionary = new Dictionary<int, string>();
dictionary.Add(1, "Hello");
dictionary.Add(2, "World");
foreach (var entry in dictionary)
{
Console.WriteLine(entry);
dictionary.Clear();
}
Console.WriteLine($"Count: {dictionary.Count}");
Run Code Online (Sandbox Code Playgroud)
输出:
[1,您好]
计数:0
预期的例外是:
InvalidOperationException:集合已被修改;枚举操作可能无法执行。
...由方法Add以及.NET Framework中的相同方法抛出。
.NET Core 3.0.0,C#8,VS 2019 16.3.1,Windows 10
这似乎是.Net完整框架和.Net core for之间的故意区别Dictionary<TKey, TValue>。
差异发生在Pull#18854中:从Dictionary中删除版本增量。删除重载:
从删除操作中删除版本增量
这解决了api更改Add Dictionary.Remove(predicate)的coreclr方面,旨在允许从字典中删除项目,同时从@jkotas枚举每个方向。相关的corefx PR中包含所有集合测试和修改的测试,以及新添加的测试。
似乎存在公开的文档问题:
可以说当前Dictionary的实现在迭代过程中支持非并发突变是否正确?
只能移除。这已作为dotnet / coreclr#18854中的功能启用。
这可以依靠未来吗
是。
我们应该确保对文档进行更新以反映这一点。
您可能想对公开文档问题进行投票,要求澄清,因为.Net core 3.0文档Dictionary<TKey,TValue>.GetEnumerator()现在已过时:
如果对集合进行了更改(例如添加,修改或删除元素),则枚举数将无法恢复,并且下一次调用
MoveNext或IEnumerator.Reset引发InvalidOperationException。
奇怪的是,在枚举期间修改字典时,确实会抛出for的枚举器。SortedDictionary<TKey, TValue>
演示:
Remove():https://dotnetfiddle.net/8vONOw(抛出)。Remove():https://dotnetfiddle.net/es6STm(不抛出)。Add():https://dotnetfiddle.net/6q7Lvx(抛出)。Remove()来自SortedDictionary<int, string>:https://dotnetfiddle.net/bssrG7(抛出)。| 归档时间: |
|
| 查看次数: |
122 次 |
| 最近记录: |