簡體   English   中英

為什么從 ConditionalWeakTable 中刪除鍵時 IEnumerator.MoveNext 不拋出?

[英]Why doesn't IEnumerator.MoveNext throw when removing keys from a ConditionalWeakTable?

即使在枚舉期間修改了枚舉集合,以下代碼也不會拋出。

using System;
using System.Collections;
using System.Runtime.CompilerServices;

namespace ConsoleApp1
{
    class MyKey
    {

    }

    class Program
    {
        static void Main(string[] args)
        {
            ConditionalWeakTable<MyKey, string> table = new();

            MyKey k1 = new();
            MyKey k2 = new();
            MyKey k3 = new();

            table.Add(k1, "v1");
            table.Add(k2, "v2");
            table.Add(k3, "v3");

            var enumerator = ((IEnumerable)table).GetEnumerator();

            while(enumerator.MoveNext()) // no exception thrown
            {
                Console.WriteLine(enumerator.Current);

                table.Remove(k1);
                table.Remove(k2);
                table.Remove(k3);
            }
        }
    }
}
[ConsoleApp1.MyKey, v1]

這是故意的,還是偶然的? 如果是前者,那么在密鑰被垃圾收集的情況下,什么會阻止拋出異常?

非常感謝!

按設計。

文檔中引用。

返回的枚舉數不會延長表中任何 object 對的生命周期,除了當前的。 它不返回已收集或檢索枚舉器后添加的條目。 此外,它可能不會返回檢索枚舉器時存在的所有條目,例如,在檢索枚舉器之后但在枚舉之前收集或刪除的條目。

枚舉器的Current屬性所指向的 object 將不會被垃圾收集並且可以安全地訪問。 如果可枚舉中的某個鍵被 GC 或刪除,則枚舉器將根本無法訪問該元素。

正如 canton7 在評論中提到的,這是ConditionalWeakTable保持線程安全所必需的 - 其他線程可能會在另一個線程的枚舉期間刪除元素。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM